From fc5b0f37a07a7439b083f247cd9c0c31a292cd16 Mon Sep 17 00:00:00 2001 From: Borja Ferrer Date: Wed, 2 Aug 2006 20:00:44 +0000 Subject: [PATCH] updated reader for latest structs more API functs, with bin search whoa :O --HG-- extra : convert_revision : svn%3A39bc706e-5318-0410-9160-8a85361fbb7c/trunk%4054 --- sourcepawn/vm/sp_reader.c | 61 +++++++---------- sourcepawn/vm/sp_vm.c | 135 ++++++++++++++++++++++++++++++++++++-- 2 files changed, 156 insertions(+), 40 deletions(-) diff --git a/sourcepawn/vm/sp_reader.c b/sourcepawn/vm/sp_reader.c index a9f5e092..504cf69c 100644 --- a/sourcepawn/vm/sp_reader.c +++ b/sourcepawn/vm/sp_reader.c @@ -7,19 +7,11 @@ sp_plugin_t *_ReadPlugin(sp_file_hdr_t *hdr, uint8_t *base, sp_plugin_t *plugin, { char *nameptr; uint8_t sectnum = 0; - - sp_plugin_infotab_t *info = (sp_plugin_infotab_t *)malloc(sizeof(sp_plugin_infotab_t)); - sp_plugin_debug_t *dbg = (sp_plugin_debug_t *)malloc(sizeof(sp_plugin_debug_t)); - sp_file_section_t *secptr = (sp_file_section_t *)(base + sizeof(sp_file_hdr_t)); memset(plugin, 0, sizeof(sp_plugin_t)); - memset(info, 0, sizeof(sp_plugin_infotab_t)); - memset(dbg, 0, sizeof(sp_plugin_debug_t)); plugin->base = base; - plugin->info = info; - plugin->debug = dbg; while (sectnum < hdr->sections) { @@ -39,57 +31,57 @@ sp_plugin_t *_ReadPlugin(sp_file_hdr_t *hdr, uint8_t *base, sp_plugin_t *plugin, plugin->data_size = dat->datasize; plugin->memory = dat->memsize; } - else if (!(plugin->info->publics) && !strcmp(nameptr, ".publics")) + else if (!(plugin->info.publics) && !strcmp(nameptr, ".publics")) { - plugin->info->publics_num = secptr->size / sizeof(sp_file_publics_t); - plugin->info->publics = (sp_file_publics_t *)(base + secptr->dataoffs); + plugin->info.publics_num = secptr->size / sizeof(sp_file_publics_t); + plugin->info.publics = (sp_file_publics_t *)(base + secptr->dataoffs); } - else if (!(plugin->info->pubvars) && !strcmp(nameptr, ".pubvars")) + else if (!(plugin->info.pubvars) && !strcmp(nameptr, ".pubvars")) { - plugin->info->pubvars_num = secptr->size / sizeof(sp_file_pubvars_t); - plugin->info->pubvars = (sp_file_pubvars_t *)(base + secptr->dataoffs); + plugin->info.pubvars_num = secptr->size / sizeof(sp_file_pubvars_t); + plugin->info.pubvars = (sp_file_pubvars_t *)(base + secptr->dataoffs); } - else if (!(plugin->info->natives) && !strcmp(nameptr, ".natives")) + else if (!(plugin->info.natives) && !strcmp(nameptr, ".natives")) { - plugin->info->natives_num = secptr->size / sizeof(sp_file_natives_t); - plugin->info->natives = (sp_file_natives_t *)(base + secptr->dataoffs); + plugin->info.natives_num = secptr->size / sizeof(sp_file_natives_t); + plugin->info.natives = (sp_file_natives_t *)(base + secptr->dataoffs); } - else if (!(plugin->info->stringbase) && !strcmp(nameptr, ".names")) + else if (!(plugin->info.stringbase) && !strcmp(nameptr, ".names")) { - plugin->info->stringbase = base + secptr->dataoffs; + plugin->info.stringbase = base + secptr->dataoffs; } - else if (!(plugin->debug->files) && !strcmp(nameptr, ".dbg.files")) + else if (!(plugin->debug.files) && !strcmp(nameptr, ".dbg.files")) { - plugin->debug->files = (sp_fdbg_file_t *)(base + secptr->dataoffs); + plugin->debug.files = (sp_fdbg_file_t *)(base + secptr->dataoffs); } - else if (!(plugin->debug->lines) && !strcmp(nameptr, ".dbg.lines")) + else if (!(plugin->debug.lines) && !strcmp(nameptr, ".dbg.lines")) { - plugin->debug->lines = (sp_fdbg_line_t *)(base + secptr->dataoffs); + plugin->debug.lines = (sp_fdbg_line_t *)(base + secptr->dataoffs); } - else if (!(plugin->debug->symbols) && !strcmp(nameptr, ".dbg.symbols")) + else if (!(plugin->debug.symbols) && !strcmp(nameptr, ".dbg.symbols")) { - plugin->debug->symbols = (sp_fdbg_symbol_t *)(base + secptr->dataoffs); + plugin->debug.symbols = (sp_fdbg_symbol_t *)(base + secptr->dataoffs); } - else if (!(plugin->debug->lines_num) && !strcmp(nameptr, ".dbg.info")) + else if (!(plugin->debug.lines_num) && !strcmp(nameptr, ".dbg.info")) { sp_fdbg_info_t *inf = (sp_fdbg_info_t *)(base + secptr->dataoffs); - plugin->debug->files_num = inf->num_files; - plugin->debug->lines_num = inf->num_lines; - plugin->debug->syms_num = inf->num_syms; + plugin->debug.files_num = inf->num_files; + plugin->debug.lines_num = inf->num_lines; + plugin->debug.syms_num = inf->num_syms; } - else if (!(plugin->debug->stringbase) && !strcmp(nameptr, ".dbg.strings")) + else if (!(plugin->debug.stringbase) && !strcmp(nameptr, ".dbg.strings")) { - plugin->debug->stringbase = base + secptr->dataoffs; + plugin->debug.stringbase = base + secptr->dataoffs; } secptr++; sectnum++; } - if (!(plugin->pcode) || !(plugin->data) || !(plugin->info->stringbase)) + if (!(plugin->pcode) || !(plugin->data) || !(plugin->info.stringbase)) goto return_error; - if ((plugin->flags == SP_FILE_DEBUG) && (!(plugin->debug->files) || !(plugin->debug->lines) || !(plugin->debug->symbols))) + if ((plugin->flags == SP_FILE_DEBUG) && (!(plugin->debug.files) || !(plugin->debug.lines) || !(plugin->debug.symbols))) goto return_error; if (err) @@ -98,9 +90,6 @@ sp_plugin_t *_ReadPlugin(sp_file_hdr_t *hdr, uint8_t *base, sp_plugin_t *plugin, return plugin; return_error: - free(dbg); - free(info); - if (err) *err = SP_ERR_FILE_FORMAT; diff --git a/sourcepawn/vm/sp_vm.c b/sourcepawn/vm/sp_vm.c index b9651fb4..d1c720e5 100644 --- a/sourcepawn/vm/sp_vm.c +++ b/sourcepawn/vm/sp_vm.c @@ -109,16 +109,143 @@ int SP_HeapRelease(sp_context_t *ctx, cell_t local_addr) int SP_FindNativeByName(sp_context_t *ctx, const char *name, uint32_t *index) { - uint32_t i; + uint32_t mid, low, high, diff; - for (i = 0; i < ctx->plugin->info->natives_num; i++) + high = ctx->plugin->info.natives_num - 1; + low = 0; + + while (low <= high) { - if (!strcmp(name, ctx->natives[i].name)) + mid = (low + high) / 2; + diff = strcmp(ctx->natives[mid].name, name); + if (diff == 0) { if (index) - *index = i; + *index = mid; return SP_ERR_NONE; + } else if (diff < 0) { + low = mid + 1; + } else { + high = mid - 1; } } + return SP_ERR_NOT_FOUND; +} + +int SP_GetNativeByIndex(sp_context_t *ctx, uint32_t index, sp_native_t **native) +{ + if (index >= ctx->plugin->info.natives_num) + return SP_ERR_INDEX; + + if (native) + *native = &(ctx->natives[index]); + + return SP_ERR_NONE; +} + +int SP_GetNativesNum(sp_context_t *ctx, uint32_t *num) +{ + *num = ctx->plugin->info.natives_num; + + return SP_ERR_NONE; +} + +int SP_FindPublicByName(sp_context_t *ctx, const char *name, uint32_t *index) +{ + uint32_t mid, low, high, diff; + + high = ctx->plugin->info.publics_num - 1; + low = 0; + + while (low <= high) + { + mid = (low + high) / 2; + diff = strcmp(ctx->publics[mid].name, name); + if (diff == 0) + { + if (index) + *index = mid; + return SP_ERR_NONE; + } else if (diff < 0) { + low = mid + 1; + } else { + high = mid - 1; + } + } + + return SP_ERR_NOT_FOUND; +} + +int SP_GetPublicByIndex(sp_context_t *ctx, uint32_t index, sp_public_t **pblic) +{ + if (index >= ctx->plugin->info.publics_num) + return SP_ERR_INDEX; + + if (pblic) + *pblic = &(ctx->publics[index]); + + return SP_ERR_NONE; +} + +int SP_GetPublicsNum(sp_context_t *ctx, uint32_t *num) +{ + *num = ctx->plugin->info.publics_num; + + return SP_ERR_NONE; +} + +int SP_GetPubvarByIndex(sp_context_t *ctx, uint32_t index, sp_pubvar_t **pubvar) +{ + if (index >= ctx->plugin->info.pubvars_num) + return SP_ERR_INDEX; + + if (pubvar) + *pubvar = &(ctx->pubvars[index]); + + return SP_ERR_NONE; +} + +int SP_FindPubvarByName(sp_context_t *ctx, const char *name, uint32_t *index) +{ + uint32_t mid, low, high, diff; + + high = ctx->plugin->info.pubvars_num - 1; + low = 0; + + while (low <= high) + { + mid = (low + high) / 2; + diff = strcmp(ctx->pubvars[mid].name, name); + if (diff == 0) + { + if (index) + *index = mid; + return SP_ERR_NONE; + } else if (diff < 0) { + low = mid + 1; + } else { + high = mid - 1; + } + } + + return SP_ERR_NOT_FOUND; +} + +int SP_GetPubvarAddrs(sp_context_t *ctx, uint32_t index, cell_t *local_addr, cell_t **phys_addr) +{ + if (index >= ctx->plugin->info.pubvars_num) + return SP_ERR_INDEX; + + *local_addr = ctx->plugin->info.pubvars[index].address; + *phys_addr = ctx->pubvars[index].offs; + + return SP_ERR_NONE; +} + +int SP_GetPubVarsNum(sp_context_t *ctx, uint32_t *num) +{ + *num = ctx->plugin->info.pubvars_num; + + return SP_ERR_NONE; } \ No newline at end of file