From 3d8f413ce8fc836c6b99f3954600c6ecb55b85bb Mon Sep 17 00:00:00 2001 From: Nguyen Anh Quynh Date: Sat, 16 Jan 2016 16:57:17 +0800 Subject: [PATCH] new API uc_mem_regions() to retrieve the list of memory regions mapped by uc_mem_map_*() --- include/unicorn/unicorn.h | 25 +++++++++++++++++++++++++ uc.c | 28 ++++++++++++++++++++++++++++ 2 files changed, 53 insertions(+) diff --git a/include/unicorn/unicorn.h b/include/unicorn/unicorn.h index 719cbcf6..e188ccc2 100644 --- a/include/unicorn/unicorn.h +++ b/include/unicorn/unicorn.h @@ -215,6 +215,14 @@ typedef void (*uc_cb_hookmem_t)(uc_engine *uc, uc_mem_type type, typedef bool (*uc_cb_eventmem_t)(uc_engine *uc, uc_mem_type type, uint64_t address, int size, int64_t value, void *user_data); +/* Memory region mapped by uc_mem_map() and uc_mem_map_ptr() + Retrieve the list of memory regions with uc_mem_regions() +*/ +typedef struct uc_mem_region { + uint64_t begin; // begin address of the region (inclusive) + uint64_t end; // end address of the region (inclusive) + uint32_t perms; // memory permissions of the region +} uc_mem_region; /* Return combined API version & major and minor version numbers. @@ -503,6 +511,23 @@ uc_err uc_mem_unmap(uc_engine *uc, uint64_t address, size_t size); UNICORN_EXPORT uc_err uc_mem_protect(uc_engine *uc, uint64_t address, size_t size, uint32_t perms); +/* + Retrieve all memory regions mapped by uc_mem_map() and uc_mem_map_ptr() + This API allocates memory for @regions, and user must free this memory later + by free() to avoid leaking memory. + NOTE: memory regions may be splitted by uc_mem_unmap() + + @handle: handle returned by uc_open() + @regions: pointer to an array of uc_mem_region struct. This is allocated by + Unicorn, and must be freed by user later + @count: pointer to number of struct uc_mem_region contained in @regions + + @return UC_ERR_OK on success, or other value on failure (refer to uc_err enum + for detailed error). +*/ +UNICORN_EXPORT +uc_err uc_mem_regions(uc_engine *handle, uc_mem_region **regions, uint32_t *count); + #ifdef __cplusplus } #endif diff --git a/uc.c b/uc.c index f88a2261..b354a5fa 100644 --- a/uc.c +++ b/uc.c @@ -1138,3 +1138,31 @@ uc_err uc_hook_del(uc_engine *uc, uc_hook hh) { return hook_del(uc, hh); } + +UNICORN_EXPORT +uint32_t uc_mem_regions(uc_engine *uc, uc_mem_region **regions, uint32_t *count) +{ + uint32_t i; + uc_mem_region *r = NULL; + + *count = uc->mapped_block_count; + + if (*count) { + r = malloc(*count * sizeof(uc_mem_region)); + if (r == NULL) { + // out of memory + return UC_ERR_NOMEM; + } + } + + for (i = 0; i < *count; i++) { + r[i].begin = uc->mapped_blocks[i]->addr; + r[i].end = uc->mapped_blocks[i]->end - 1; + r[i].perms = uc->mapped_blocks[i]->perms; + } + + *regions = r; + + return UC_ERR_OK; +} +