From 49d339e42489732c733016df789eca4d905ef618 Mon Sep 17 00:00:00 2001 From: York Jasper Niebuhr Date: Sun, 26 Oct 2025 23:02:13 +0100 Subject: [PATCH] Selfpatch target collection --- selfpatch/src/selfpatch.c | 4 +- selfpatch/src/targets.c | 120 +++++++++++++++++++++++++++++++++++++- selfpatch/src/targets.h | 2 + 3 files changed, 123 insertions(+), 3 deletions(-) diff --git a/selfpatch/src/selfpatch.c b/selfpatch/src/selfpatch.c index f6a0bd0..7767bdc 100644 --- a/selfpatch/src/selfpatch.c +++ b/selfpatch/src/selfpatch.c @@ -68,8 +68,10 @@ void spslr_selfpatch() { int sz; struct SPSLR_INST inst; while ((sz = spslr_inst_load(&inst, __spslr_program)) > 0) { - if (inst.opcode == SPSLR_EXIT) + if (inst.opcode == SPSLR_EXIT) { + spslr_targets_clear(); return; + } if (spslr_do(&inst) < 0) { fprintf(stderr, "spslr_selfpatch failed to execute an instruction\n"); diff --git a/selfpatch/src/targets.c b/selfpatch/src/targets.c index 6e761dd..8351364 100644 --- a/selfpatch/src/targets.c +++ b/selfpatch/src/targets.c @@ -1,16 +1,132 @@ #include "targets.h" -// TODO +#include -int spslr_target(uint32_t uid, uint32_t size, uint32_t fieldcnt) { +struct Field { + uint32_t initial_offset; + uint32_t initial_idx; + + uint32_t offset; + uint32_t size; + uint32_t flags; +}; + +struct FinalField { + uint32_t initial_offset; + uint32_t offset; +}; + +struct Target { + uint32_t uid; + uint32_t size; + uint32_t field_count; + + uint32_t present_field_count; + struct Field* fields; + struct FinalField* final_fields; // After rand (indexable by initial layout) + + struct Target* next; +}; + +static struct Target* targets = NULL; + +static struct Target* find_target(uint32_t uid) { + struct Target* cur = targets; + while (cur) { + if (cur->uid == uid) + return cur; + + cur = cur->next; + } + + return NULL; +} + +static int add_target(uint32_t uid, uint32_t size, uint32_t fieldcnt) { + if (find_target(uid)) + return -1; + + struct Target* new_target = (struct Target*)malloc(sizeof(struct Target)); + if (!new_target) + return -1; + + new_target->uid = uid; + new_target->size = size; + new_target->field_count = fieldcnt; + + new_target->present_field_count = 0; + new_target->final_fields = NULL; + new_target->fields = (struct Field*)malloc(sizeof(struct Field) * fieldcnt); + + if (!new_target->fields) { + free(new_target); + return -1; + } + + new_target->next = targets; + targets = new_target; return 0; } +static void clear_targets() { + struct Target* cur = targets; + while (cur) { + if (cur->fields) + free(cur->fields); + if (cur->final_fields) + free(cur->final_fields); + + struct Target* tmp = cur; + cur = cur->next; + + free(tmp); + } + + targets = NULL; +} + +int spslr_target(uint32_t uid, uint32_t size, uint32_t fieldcnt) { + if (find_target(uid)) + return -1; + + return add_target(uid, size, fieldcnt); +} + int spslr_field(uint32_t target, uint32_t offset, uint32_t size, uint32_t flags) { + struct Target* t = find_target(target); + if (!t) + return -1; + + if (offset + size > t->size) + return -1; + + if (t->present_field_count >= t->field_count) + return -1; + + if (t->present_field_count) { + struct Field* pred = &t->fields[t->present_field_count - 1]; + if (offset < pred->offset + pred->size) + return -1; + } + + uint32_t idx = t->present_field_count++; + + struct Field* f = &t->fields[idx]; + f->initial_offset = offset; + f->initial_idx = idx; + f->offset = offset; + f->size = size; + f->flags = flags; + return 0; } int spslr_randomize(uint32_t target) { + // TODO return 0; } +void spslr_targets_clear() { + clear_targets(); +} + diff --git a/selfpatch/src/targets.h b/selfpatch/src/targets.h index 6cef7bc..30566ae 100644 --- a/selfpatch/src/targets.h +++ b/selfpatch/src/targets.h @@ -7,4 +7,6 @@ int spslr_target(uint32_t uid, uint32_t size, uint32_t fieldcnt); int spslr_field(uint32_t target, uint32_t offset, uint32_t size, uint32_t flags); int spslr_randomize(uint32_t target); +void spslr_targets_clear(); + #endif