Switch from selfpatch panic to errors
This commit is contained in:
parent
ffad62e9d6
commit
5ad79087a6
@ -8,6 +8,30 @@
|
||||
#define SPSLR_MODULE_SYM_DPIN_CNT "spslr_dpin_cnt"
|
||||
#define SPSLR_MODULE_SYM_DPINS "spslr_dpins"
|
||||
|
||||
enum spslr_viability {
|
||||
SPSLR_VIABLE,
|
||||
SPSLR_NONVIABLE
|
||||
};
|
||||
|
||||
enum spslr_error {
|
||||
SPSLR_OK,
|
||||
SPSLR_ERROR_RANDOMIZER_INIT,
|
||||
SPSLR_ERROR_INITIAL_TARGET_LAYOUT,
|
||||
SPSLR_ERROR_RANDOMIZED_TARGET_LAYOUT,
|
||||
SPSLR_ERROR_RANDOMIZE,
|
||||
SPSLR_ERROR_REORDER_BUFFER,
|
||||
SPSLR_ERROR_UNINITIALIZED,
|
||||
SPSLR_ERROR_ALREADY_PATCHED,
|
||||
SPSLR_ERROR_PATCH_DPINS,
|
||||
SPSLR_ERROR_PATCH_IPINS,
|
||||
SPSLR_ERROR_META_INCOMPLETE
|
||||
};
|
||||
|
||||
struct spslr_status {
|
||||
enum spslr_viability viability;
|
||||
enum spslr_error error;
|
||||
};
|
||||
|
||||
struct spslr_module {
|
||||
const void* ipin_cnt;
|
||||
const void* ipins;
|
||||
@ -17,9 +41,8 @@ struct spslr_module {
|
||||
const void* dpins;
|
||||
};
|
||||
|
||||
void spslr_init(void);
|
||||
void spslr_selfpatch(void);
|
||||
void spslr_patch_module(const struct spslr_module* m);
|
||||
void spslr_cleanup(void);
|
||||
struct spslr_status spslr_init(void);
|
||||
struct spslr_status spslr_selfpatch(void);
|
||||
struct spslr_status spslr_patch_module(const struct spslr_module* m);
|
||||
|
||||
#endif
|
||||
|
||||
@ -6,67 +6,79 @@
|
||||
|
||||
#define SPSLR_SANITY_CHECK
|
||||
|
||||
static void spslr_patch_dpins(const struct spslr_dpin* dpins, spslr_u32 cnt);
|
||||
static void spslr_patch_dpin(void* addr, spslr_u32 target);
|
||||
static void spslr_patch_ipins(const struct spslr_ipin* ipins, spslr_u32 cnt,
|
||||
static int spslr_patch_dpins(const struct spslr_dpin* dpins, spslr_u32 cnt);
|
||||
static int spslr_patch_dpin(void* addr, spslr_u32 target);
|
||||
static int spslr_patch_ipins(const struct spslr_ipin* ipins, spslr_u32 cnt,
|
||||
const struct spslr_ipin_op* ipin_ops, spslr_u32 op_cnt);
|
||||
|
||||
static void reorder_object(void* dst, const void* src, spslr_u32 target);
|
||||
static spslr_s64 spslr_calculate_ipin_value(const struct spslr_ipin_op* ipin_ops, spslr_u32 op_cnt, spslr_u32 start);
|
||||
static int reorder_object(void* dst, const void* src, spslr_u32 target);
|
||||
static int spslr_calculate_ipin_value(const struct spslr_ipin_op* ipin_ops, spslr_u32 op_cnt, spslr_u32 start, spslr_s64* res);
|
||||
|
||||
static void* reorder_buffer = NULL;
|
||||
|
||||
static void allocate_reorder_buffer(void);
|
||||
static void release_reorder_buffer(void);
|
||||
static int allocate_reorder_buffer(void);
|
||||
|
||||
static int initialized = 0;
|
||||
static int initialized = 0, patched = 0;
|
||||
static enum spslr_viability viable = SPSLR_VIABLE;
|
||||
|
||||
void __init spslr_init(void) {
|
||||
struct spslr_status __init spslr_init(void) {
|
||||
if (initialized)
|
||||
return;
|
||||
return (struct spslr_status) { .viability = viable, .error = SPSLR_OK };
|
||||
|
||||
if (spslr_randomizer_init() < 0)
|
||||
spslr_env_panic("failed to initialize randomizer");
|
||||
return (struct spslr_status) { .viability = viable, .error = SPSLR_ERROR_RANDOMIZER_INIT };
|
||||
|
||||
#ifdef SPSLR_SANITY_CHECK
|
||||
for (spslr_u32 tidx = 0; tidx < spslr_target_cnt; tidx++) {
|
||||
if (spslr_randomizer_validate_target(tidx) < 0)
|
||||
spslr_env_panic("original layout of target %u is invalid", tidx);
|
||||
return (struct spslr_status) { .viability = viable, .error = SPSLR_ERROR_INITIAL_TARGET_LAYOUT };
|
||||
}
|
||||
#endif
|
||||
|
||||
if (spslr_randomize() < 0)
|
||||
spslr_env_panic("failed to randomize targets");
|
||||
return (struct spslr_status) { .viability = viable, .error = SPSLR_ERROR_RANDOMIZE };
|
||||
|
||||
#ifdef SPSLR_SANITY_CHECK
|
||||
for (spslr_u32 tidx = 0; tidx < spslr_target_cnt; tidx++) {
|
||||
if (spslr_randomizer_debug_target(tidx) < 0)
|
||||
spslr_env_panic("failed to debug print final layout of target %u", tidx);
|
||||
|
||||
if (spslr_randomizer_validate_target(tidx) < 0)
|
||||
spslr_env_panic("final layout of target %u is invalid", tidx);
|
||||
return (struct spslr_status) { .viability = viable, .error = SPSLR_ERROR_RANDOMIZED_TARGET_LAYOUT };
|
||||
}
|
||||
#endif
|
||||
|
||||
allocate_reorder_buffer();
|
||||
if (allocate_reorder_buffer() < 0)
|
||||
return (struct spslr_status) { .viability = viable, .error = SPSLR_ERROR_REORDER_BUFFER };
|
||||
|
||||
initialized = 1;
|
||||
return (struct spslr_status) { .viability = viable, .error = SPSLR_OK };
|
||||
}
|
||||
|
||||
void __init spslr_selfpatch(void) {
|
||||
if (!initialized)
|
||||
spslr_env_panic("tried to selfpatchpatch with uninitialized spslr context");
|
||||
struct spslr_status __init spslr_selfpatch(void) {
|
||||
if (patched)
|
||||
return (struct spslr_status) { .viability = viable, .error = SPSLR_ERROR_ALREADY_PATCHED };
|
||||
|
||||
spslr_patch_dpins(spslr_dpins, spslr_dpin_cnt);
|
||||
spslr_patch_ipins(spslr_ipins, spslr_ipin_cnt, spslr_ipin_ops, spslr_ipin_op_cnt);
|
||||
if (!initialized)
|
||||
return (struct spslr_status) { .viability = viable, .error = SPSLR_ERROR_UNINITIALIZED };
|
||||
|
||||
viable = SPSLR_NONVIABLE;
|
||||
|
||||
if (spslr_patch_dpins(spslr_dpins, spslr_dpin_cnt) < 0)
|
||||
return (struct spslr_status) { .viability = viable, .error = SPSLR_ERROR_PATCH_DPINS };
|
||||
|
||||
if (spslr_patch_ipins(spslr_ipins, spslr_ipin_cnt, spslr_ipin_ops, spslr_ipin_op_cnt) < 0)
|
||||
return (struct spslr_status) { .viability = viable, .error = SPSLR_ERROR_PATCH_IPINS };
|
||||
|
||||
viable = SPSLR_VIABLE;
|
||||
|
||||
patched = 1;
|
||||
return (struct spslr_status) { .viability = viable, .error = SPSLR_OK };
|
||||
}
|
||||
|
||||
void __init spslr_patch_module(const struct spslr_module* m) {
|
||||
struct spslr_status __init spslr_patch_module(const struct spslr_module* m) {
|
||||
if (!initialized)
|
||||
spslr_env_panic("tried to patch module with uninitialized spslr context");
|
||||
return (struct spslr_status) { .viability = SPSLR_VIABLE, .error = SPSLR_ERROR_UNINITIALIZED };
|
||||
|
||||
if (!m || !m->ipin_cnt || !m->ipins || !m->ipin_op_cnt || !m->ipin_ops || !m->dpin_cnt || !m->dpins)
|
||||
spslr_env_panic("tried to patch module with incomplete spslr data");
|
||||
return (struct spslr_status) { .viability = SPSLR_VIABLE, .error = SPSLR_ERROR_META_INCOMPLETE };
|
||||
|
||||
spslr_u32 module_ipin_cnt = *(const spslr_u32*)m->ipin_cnt;
|
||||
const struct spslr_ipin* module_ipins = (const struct spslr_ipin*)m->ipins;
|
||||
@ -75,23 +87,18 @@ void __init spslr_patch_module(const struct spslr_module* m) {
|
||||
spslr_u32 module_dpin_cnt = *(const spslr_u32*)m->dpin_cnt;
|
||||
const struct spslr_dpin* module_dpins = (const struct spslr_dpin*)m->dpins;
|
||||
|
||||
spslr_patch_dpins(module_dpins, module_dpin_cnt);
|
||||
spslr_patch_ipins(module_ipins, module_ipin_cnt, module_ipin_ops, module_ipin_op_cnt);
|
||||
if (spslr_patch_dpins(module_dpins, module_dpin_cnt) < 0)
|
||||
return (struct spslr_status) { .viability = SPSLR_NONVIABLE, .error = SPSLR_ERROR_PATCH_DPINS };
|
||||
|
||||
if (spslr_patch_ipins(module_ipins, module_ipin_cnt, module_ipin_ops, module_ipin_op_cnt) < 0)
|
||||
return (struct spslr_status) { .viability = SPSLR_NONVIABLE, .error = SPSLR_ERROR_PATCH_IPINS };
|
||||
|
||||
return (struct spslr_status) { .viability = SPSLR_VIABLE, .error = SPSLR_OK };
|
||||
}
|
||||
|
||||
void __init spslr_cleanup(void) {
|
||||
if (!initialized)
|
||||
spslr_env_panic("tried to clean up uninitialized spslr context");
|
||||
|
||||
initialized = 0;
|
||||
|
||||
release_reorder_buffer();
|
||||
spslr_randomizer_clear();
|
||||
}
|
||||
|
||||
static void __init allocate_reorder_buffer(void) {
|
||||
static int __init allocate_reorder_buffer(void) {
|
||||
if (reorder_buffer)
|
||||
return;
|
||||
return 0;
|
||||
|
||||
spslr_u32 max_target_size = 0;
|
||||
for (spslr_u32 i = 0; i < spslr_target_cnt; i++) {
|
||||
@ -101,28 +108,25 @@ static void __init allocate_reorder_buffer(void) {
|
||||
|
||||
reorder_buffer = spslr_env_malloc(max_target_size);
|
||||
if (!reorder_buffer)
|
||||
spslr_env_panic("failed to allocate reorder buffer of size %u", max_target_size);
|
||||
return -1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void __init release_reorder_buffer(void) {
|
||||
if (!reorder_buffer)
|
||||
return;
|
||||
|
||||
spslr_env_free(reorder_buffer);
|
||||
reorder_buffer = NULL;
|
||||
}
|
||||
|
||||
static void __init spslr_patch_dpins(const struct spslr_dpin* dpins, spslr_u32 cnt) {
|
||||
static int __init spslr_patch_dpins(const struct spslr_dpin* dpins, spslr_u32 cnt) {
|
||||
for (spslr_u32 dpidx = 0; dpidx < cnt; dpidx++) {
|
||||
const struct spslr_dpin* dp = &dpins[dpidx];
|
||||
spslr_patch_dpin((void*)dp->addr, dp->target);
|
||||
if (spslr_patch_dpin((void*)dp->addr, dp->target) < 0)
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void __init reorder_object(void* dst, const void* src, spslr_u32 target) {
|
||||
static int __init reorder_object(void* dst, const void* src, spslr_u32 target) {
|
||||
spslr_u32 field_count;
|
||||
if (spslr_randomizer_get_target(target, NULL, &field_count))
|
||||
spslr_env_panic("failed to get field count of target %u", target);
|
||||
return -1;
|
||||
|
||||
const spslr_u8* src_countable = (const spslr_u8*)src;
|
||||
spslr_u8* dst_countable = (spslr_u8*)dst;
|
||||
@ -130,62 +134,75 @@ static void __init reorder_object(void* dst, const void* src, spslr_u32 target)
|
||||
for (spslr_u32 i = 0; i < field_count; i++) {
|
||||
struct spslr_randomizer_field_info finfo;
|
||||
if (spslr_randomizer_get_field(target, i, SPSLR_RANDOMIZER_FIELD_IDX_MODE_FINAL, &finfo))
|
||||
spslr_env_panic("failed to get descriptor of final field %u of target %u", i, target);
|
||||
return -1;
|
||||
|
||||
spslr_env_memcpy(dst_countable + finfo.offset, src_countable + finfo.initial_offset, finfo.size);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void __init spslr_patch_dpin(void* addr, spslr_u32 target) {
|
||||
#ifdef SPSLR_SANITY_CHECK
|
||||
static int __init spslr_patch_dpin(void* addr, spslr_u32 target) {
|
||||
if (target >= spslr_target_cnt)
|
||||
spslr_env_panic("dpin refers to invalid target %u", target);
|
||||
#endif
|
||||
return -1;
|
||||
|
||||
const struct spslr_target* t = &spslr_targets[target];
|
||||
|
||||
spslr_env_memset(reorder_buffer, 0, t->size);
|
||||
reorder_object(reorder_buffer, addr, target);
|
||||
spslr_env_poke_data(addr, reorder_buffer, t->size);
|
||||
|
||||
if (reorder_object(reorder_buffer, addr, target) < 0)
|
||||
return -1;
|
||||
|
||||
if (spslr_env_poke_data(addr, reorder_buffer, t->size) < 0)
|
||||
return -1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void __init spslr_patch_ipins(const struct spslr_ipin* ipins, spslr_u32 cnt,
|
||||
static int __init spslr_patch_ipins(const struct spslr_ipin* ipins, spslr_u32 cnt,
|
||||
const struct spslr_ipin_op* ipin_ops, spslr_u32 op_cnt) {
|
||||
for (spslr_u32 ipidx = 0; ipidx < cnt; ipidx++) {
|
||||
const struct spslr_ipin* ip = &ipins[ipidx];
|
||||
|
||||
spslr_s64 value = spslr_calculate_ipin_value(ipin_ops, op_cnt, ip->program);
|
||||
spslr_s64 value;
|
||||
if (spslr_calculate_ipin_value(ipin_ops, op_cnt, ip->program, &value) < 0)
|
||||
return -1;
|
||||
|
||||
switch (ip->size) {
|
||||
case 1:
|
||||
spslr_env_poke_text_8((void*)ip->addr, (spslr_u8)value);
|
||||
if (spslr_env_poke_text_8((void*)ip->addr, (spslr_u8)value) < 0)
|
||||
return -1;
|
||||
break;
|
||||
case 2:
|
||||
spslr_env_poke_text_16((void*)ip->addr, (spslr_u16)value);
|
||||
if (spslr_env_poke_text_16((void*)ip->addr, (spslr_u16)value) < 0)
|
||||
return -1;
|
||||
break;
|
||||
case 4:
|
||||
spslr_env_poke_text_32((void*)ip->addr, (spslr_u32)value);
|
||||
if (spslr_env_poke_text_32((void*)ip->addr, (spslr_u32)value) < 0)
|
||||
return -1;
|
||||
break;
|
||||
case 8:
|
||||
spslr_env_poke_text_64((void*)ip->addr, (spslr_u64)value);
|
||||
if (spslr_env_poke_text_64((void*)ip->addr, (spslr_u64)value) < 0)
|
||||
return -1;
|
||||
break;
|
||||
#ifdef SPSLR_SANITY_CHECK
|
||||
default:
|
||||
spslr_env_panic("invalid ipin size of %u bytes", ip->size);
|
||||
#endif
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static spslr_s64 __init spslr_calculate_ipin_value(const struct spslr_ipin_op* ipin_ops, spslr_u32 op_cnt, spslr_u32 start) {
|
||||
spslr_s64 res = 0;
|
||||
static int __init spslr_calculate_ipin_value(const struct spslr_ipin_op* ipin_ops, spslr_u32 op_cnt, spslr_u32 start, spslr_s64* res) {
|
||||
if (!res)
|
||||
return -1;
|
||||
|
||||
*res = 0;
|
||||
|
||||
spslr_u32 pc = start;
|
||||
while (1) {
|
||||
#ifdef SPSLR_SANITY_CHECK
|
||||
if (pc >= op_cnt)
|
||||
spslr_env_panic("ipin op %u out of bounds", pc);
|
||||
#endif
|
||||
return -1;
|
||||
|
||||
int end_flag = 0;
|
||||
|
||||
@ -199,10 +216,9 @@ static spslr_s64 __init spslr_calculate_ipin_value(const struct spslr_ipin_op* i
|
||||
struct spslr_randomizer_field_info finfo;
|
||||
if (spslr_randomizer_get_field(op->op0.add_initial_offset_target,
|
||||
op->op1.add_initial_offset_field, SPSLR_RANDOMIZER_FIELD_IDX_MODE_ORIGINAL, &finfo))
|
||||
spslr_env_panic("failed to get info of initial field %u of target %u",
|
||||
op->op1.add_initial_offset_field, op->op0.add_initial_offset_target);
|
||||
return -1;
|
||||
|
||||
res += finfo.initial_offset;
|
||||
*res += finfo.initial_offset;
|
||||
}
|
||||
break;
|
||||
case SPSLR_IPIN_OP_ADD_OFFSET:
|
||||
@ -210,10 +226,9 @@ static spslr_s64 __init spslr_calculate_ipin_value(const struct spslr_ipin_op* i
|
||||
struct spslr_randomizer_field_info finfo;
|
||||
if (spslr_randomizer_get_field(op->op0.add_offset_target,
|
||||
op->op1.add_offset_field, SPSLR_RANDOMIZER_FIELD_IDX_MODE_ORIGINAL, &finfo))
|
||||
spslr_env_panic("failed to get info of initial field %u of target %u",
|
||||
op->op1.add_offset_field, op->op0.add_offset_target);
|
||||
return -1;
|
||||
|
||||
res += finfo.offset;
|
||||
*res += finfo.offset;
|
||||
}
|
||||
break;
|
||||
case SPSLR_IPIN_OP_SUB_INITIAL_OFFSET:
|
||||
@ -221,10 +236,9 @@ static spslr_s64 __init spslr_calculate_ipin_value(const struct spslr_ipin_op* i
|
||||
struct spslr_randomizer_field_info finfo;
|
||||
if (spslr_randomizer_get_field(op->op0.sub_initial_offset_target,
|
||||
op->op1.sub_initial_offset_field, SPSLR_RANDOMIZER_FIELD_IDX_MODE_ORIGINAL, &finfo))
|
||||
spslr_env_panic("failed to get info of initial field %u of target %u",
|
||||
op->op1.sub_initial_offset_field, op->op0.sub_initial_offset_target);
|
||||
return -1;
|
||||
|
||||
res -= finfo.initial_offset;
|
||||
*res -= finfo.initial_offset;
|
||||
}
|
||||
break;
|
||||
case SPSLR_IPIN_OP_SUB_OFFSET:
|
||||
@ -232,25 +246,22 @@ static spslr_s64 __init spslr_calculate_ipin_value(const struct spslr_ipin_op* i
|
||||
struct spslr_randomizer_field_info finfo;
|
||||
if (spslr_randomizer_get_field(op->op0.sub_offset_target,
|
||||
op->op1.sub_offset_field, SPSLR_RANDOMIZER_FIELD_IDX_MODE_ORIGINAL, &finfo))
|
||||
spslr_env_panic("failed to get info of initial field %u of target %u",
|
||||
op->op1.sub_offset_field, op->op0.sub_offset_target);
|
||||
return -1;
|
||||
|
||||
res -= finfo.offset;
|
||||
*res -= finfo.offset;
|
||||
}
|
||||
break;
|
||||
case SPSLR_IPIN_OP_ADD_CONST:
|
||||
res += op->op0.add_const_value;
|
||||
*res += op->op0.add_const_value;
|
||||
break;
|
||||
#ifdef SPSLR_SANITY_CHECK
|
||||
default:
|
||||
spslr_env_panic("invalid ipin op");
|
||||
#endif
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (end_flag)
|
||||
break;
|
||||
}
|
||||
|
||||
return res;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
@ -44,10 +44,10 @@ static int __init spslr_env_get_prot(void* addr, int* prot) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
static void __init spslr_env_poke_safe(void* dst, const void* src, spslr_u32 n) {
|
||||
static int __init spslr_env_poke_safe(void* dst, const void* src, spslr_u32 n) {
|
||||
int original_prot;
|
||||
if (spslr_env_get_prot(dst, &original_prot))
|
||||
spslr_env_panic("failed to get prot of text poke destination %p", dst);
|
||||
return -1;
|
||||
|
||||
spslr_u64 ptr_uint = (spslr_u64)dst;
|
||||
spslr_u64 ptr_page = ptr_uint & PAGE_MASK;
|
||||
@ -62,62 +62,32 @@ static void __init spslr_env_poke_safe(void* dst, const void* src, spslr_u32 n)
|
||||
|
||||
if (tmp_prot != original_prot)
|
||||
mprotect((void*)ptr_page, prot_size, original_prot);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void __init spslr_env_panic(const char* fmt, ...) {
|
||||
va_list args;
|
||||
va_start(args, fmt);
|
||||
|
||||
fprintf(stderr, "[spslr_panic] ");
|
||||
vfprintf(stderr, fmt, args);
|
||||
fprintf(stderr, "\n");
|
||||
|
||||
va_end(args);
|
||||
|
||||
exit(1);
|
||||
int __init spslr_env_poke_text_8(void* dst, spslr_u8 value) {
|
||||
return spslr_env_poke_safe(dst, &value, sizeof(value));
|
||||
}
|
||||
|
||||
void __init spslr_env_debug(const char* fmt, ...) {
|
||||
va_list args;
|
||||
va_start(args, fmt);
|
||||
|
||||
fprintf(stdout, "[spslr_debug] ");
|
||||
vfprintf(stdout, fmt, args);
|
||||
fprintf(stdout, "\n");
|
||||
|
||||
va_end(args);
|
||||
int __init spslr_env_poke_text_16(void* dst, spslr_u16 value) {
|
||||
return spslr_env_poke_safe(dst, &value, sizeof(value));
|
||||
}
|
||||
|
||||
void __init spslr_env_poke_text_8(void* dst, spslr_u8 value) {
|
||||
spslr_env_poke_safe(dst, &value, sizeof(value));
|
||||
int __init spslr_env_poke_text_32(void* dst, spslr_u32 value) {
|
||||
return spslr_env_poke_safe(dst, &value, sizeof(value));
|
||||
}
|
||||
|
||||
void __init spslr_env_poke_text_16(void* dst, spslr_u16 value) {
|
||||
spslr_env_poke_safe(dst, &value, sizeof(value));
|
||||
}
|
||||
|
||||
void __init spslr_env_poke_text_32(void* dst, spslr_u32 value) {
|
||||
spslr_env_poke_safe(dst, &value, sizeof(value));
|
||||
}
|
||||
|
||||
void __init spslr_env_poke_text_64(void* dst, spslr_u64 value) {
|
||||
spslr_env_poke_safe(dst, &value, sizeof(value));
|
||||
int __init spslr_env_poke_text_64(void* dst, spslr_u64 value) {
|
||||
return spslr_env_poke_safe(dst, &value, sizeof(value));
|
||||
}
|
||||
|
||||
void* __init spslr_env_malloc(spslr_u32 n) {
|
||||
void* res = malloc(n);
|
||||
if (!res)
|
||||
spslr_env_panic("malloc of size %u failed", n);
|
||||
|
||||
return res;
|
||||
return malloc(n);
|
||||
}
|
||||
|
||||
void __init spslr_env_free(void* ptr) {
|
||||
free(ptr);
|
||||
}
|
||||
|
||||
void __init spslr_env_poke_data(void* dst, const void* src, spslr_u32 n) {
|
||||
spslr_env_poke_safe(dst, src, n);
|
||||
int __init spslr_env_poke_data(void* dst, const void* src, spslr_u32 n) {
|
||||
return spslr_env_poke_safe(dst, src, n);
|
||||
}
|
||||
|
||||
void __init spslr_env_memset(void* dst, int v, spslr_u32 n) {
|
||||
|
||||
@ -12,10 +12,6 @@
|
||||
#define __init /* only required in kernel */
|
||||
#endif
|
||||
|
||||
#ifndef __noreturn
|
||||
#define __noreturn __attribute__((noreturn))
|
||||
#endif
|
||||
|
||||
#ifndef __printf
|
||||
#define __printf(fmt_pos, arg_pos) __attribute__((format(printf, fmt_pos, arg_pos)))
|
||||
#endif
|
||||
@ -32,16 +28,12 @@ typedef int32_t spslr_s32;
|
||||
typedef int64_t spslr_s64;
|
||||
typedef uintptr_t spslr_uintptr;
|
||||
|
||||
void __noreturn spslr_env_panic(const char* fmt, ...) __printf(1, 2);
|
||||
void spslr_env_debug(const char* fmt, ...) __printf(1, 2);
|
||||
|
||||
void spslr_env_poke_text_8(void* dst, spslr_u8 value);
|
||||
void spslr_env_poke_text_16(void* dst, spslr_u16 value);
|
||||
void spslr_env_poke_text_32(void* dst, spslr_u32 value);
|
||||
void spslr_env_poke_text_64(void* dst, spslr_u64 value);
|
||||
int spslr_env_poke_text_8(void* dst, spslr_u8 value);
|
||||
int spslr_env_poke_text_16(void* dst, spslr_u16 value);
|
||||
int spslr_env_poke_text_32(void* dst, spslr_u32 value);
|
||||
int spslr_env_poke_text_64(void* dst, spslr_u64 value);
|
||||
int spslr_env_poke_data(void* dst, const void* src, spslr_u32 n);
|
||||
void* spslr_env_malloc(spslr_u32 n); // Either return valid buffer or panic internally
|
||||
void spslr_env_free(void* ptr);
|
||||
void spslr_env_poke_data(void* dst, const void* src, spslr_u32 n);
|
||||
void spslr_env_memset(void* dst, int v, spslr_u32 n);
|
||||
void spslr_env_memcpy(void* dst, const void* src, spslr_u32 n);
|
||||
spslr_u32 spslr_env_random_u32(void);
|
||||
|
||||
@ -34,14 +34,6 @@ int __init spslr_randomizer_init(void) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
void __init spslr_randomizer_clear(void) {
|
||||
if (!fields)
|
||||
return;
|
||||
|
||||
spslr_env_free(fields);
|
||||
fields = NULL;
|
||||
}
|
||||
|
||||
int __init spslr_randomizer_get_target(spslr_u32 target, spslr_u32* size, spslr_u32* fieldcnt) {
|
||||
if (target >= spslr_target_cnt)
|
||||
return -1;
|
||||
@ -95,26 +87,6 @@ int __init spslr_randomizer_get_field(spslr_u32 target, spslr_u32 field, int fie
|
||||
return 0;
|
||||
}
|
||||
|
||||
int __init spslr_randomizer_debug_target(spslr_u32 target) {
|
||||
spslr_u32 size, fieldcnt;
|
||||
|
||||
if (spslr_randomizer_get_target(target, &size, &fieldcnt) < 0)
|
||||
return -1;
|
||||
|
||||
spslr_env_debug("Target %u (%u fields, %u bytes):", target, fieldcnt, size);
|
||||
|
||||
for (spslr_u32 i = 0; i < fieldcnt; i++) {
|
||||
struct spslr_randomizer_field_info finfo;
|
||||
if (spslr_randomizer_get_field(target, i, SPSLR_RANDOMIZER_FIELD_IDX_MODE_ORIGINAL, &finfo) < 0)
|
||||
return -1;
|
||||
|
||||
spslr_env_debug(" Field %u (%u bytes) moved from offset %u to %u", i,
|
||||
finfo.size, finfo.initial_offset, finfo.offset);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int __init spslr_randomizer_validate_target(spslr_u32 target) {
|
||||
spslr_u32 tsize, fieldcnt;
|
||||
|
||||
|
||||
@ -16,13 +16,11 @@ struct spslr_randomizer_field_info {
|
||||
|
||||
int spslr_randomizer_init(void);
|
||||
int spslr_randomize(void);
|
||||
void spslr_randomizer_clear(void);
|
||||
|
||||
int spslr_randomizer_get_target(spslr_u32 target, spslr_u32* size, spslr_u32* fieldcnt);
|
||||
int spslr_randomizer_get_field(spslr_u32 target, spslr_u32 field, int field_idx_mode,
|
||||
struct spslr_randomizer_field_info* info);
|
||||
|
||||
int spslr_randomizer_debug_target(spslr_u32 target);
|
||||
int spslr_randomizer_validate_target(spslr_u32 target);
|
||||
|
||||
#endif
|
||||
|
||||
@ -19,17 +19,6 @@ spslr_u32 spslr_env_random_u32(void) {
|
||||
return ((spslr_u32)rand() << 16) ^ (spslr_u32)rand();
|
||||
}
|
||||
|
||||
void __init spslr_env_debug(const char* fmt, ...) {
|
||||
va_list args;
|
||||
va_start(args, fmt);
|
||||
|
||||
fprintf(stdout, "[spslr_debug] ");
|
||||
vfprintf(stdout, fmt, args);
|
||||
fprintf(stdout, "\n");
|
||||
|
||||
va_end(args);
|
||||
}
|
||||
|
||||
const spslr_u32 spslr_target_cnt = 1;
|
||||
const spslr_u32 spslr_target_field_cnt = 196;
|
||||
|
||||
@ -284,29 +273,24 @@ static int check_target(spslr_u32 tidx) {
|
||||
int main(void) {
|
||||
srand((unsigned)time(NULL));
|
||||
|
||||
spslr_u32 rounds = 100;
|
||||
|
||||
for (spslr_u32 iter = 0; iter < rounds; iter++) {
|
||||
if (spslr_randomizer_init() < 0) {
|
||||
fprintf(stderr, "init failed\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (spslr_randomize() < 0) {
|
||||
fprintf(stderr, "randomize failed at iter %u\n", iter);
|
||||
fprintf(stderr, "randomize failed\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
for (spslr_u32 tidx = 0; tidx < spslr_target_cnt; tidx++) {
|
||||
if (check_target(tidx) < 0) {
|
||||
fprintf(stderr, "check failed at iter %u target %u\n", iter, tidx);
|
||||
fprintf(stderr, "check failed at target %u\n", tidx);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
spslr_randomizer_clear();
|
||||
}
|
||||
printf("OK\n");
|
||||
|
||||
printf("ok: %u iterations\n", rounds);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -71,7 +71,12 @@ static int do_module_test_access_pid(const char *path, const struct task_struct
|
||||
return -1;
|
||||
}
|
||||
|
||||
spslr_patch_module(&mod);
|
||||
struct spslr_status spslr_success = spslr_patch_module(&mod);
|
||||
if (spslr_success.error != SPSLR_OK) {
|
||||
fprintf(stderr, "failed to patch module\n");
|
||||
dlclose(handle);
|
||||
return -1;
|
||||
}
|
||||
|
||||
module_test_access_fn fn = (module_test_access_fn)dlsym(handle, "module_test_access_pid");
|
||||
|
||||
@ -112,8 +117,19 @@ void arr_test() {
|
||||
|
||||
int main(void)
|
||||
{
|
||||
spslr_init();
|
||||
spslr_selfpatch();
|
||||
struct spslr_status spslr_success;
|
||||
|
||||
spslr_success = spslr_init();
|
||||
if (spslr_success.error != SPSLR_OK) {
|
||||
fprintf(stderr, "Failed to initialize spslr!\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
spslr_success = spslr_selfpatch();
|
||||
if (spslr_success.error != SPSLR_OK) {
|
||||
fprintf(stderr, "Failed to selfpatch!\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
print_layout();
|
||||
|
||||
@ -152,7 +168,6 @@ int main(void)
|
||||
int module_pid = do_module_test_access_pid("./subject/libspslr_module.so", &global);
|
||||
printf("module_test_access returned %d (should be 42)\n", module_pid);
|
||||
|
||||
spslr_cleanup();
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
Loading…
Reference in New Issue
Block a user