diff options
-rw-r--r-- | include/perk/perk.h | 7 | ||||
-rw-r--r-- | include/perk/perk_meta.h | 16 | ||||
-rw-r--r-- | project/common.mk | 1 | ||||
-rw-r--r-- | src/logic/pe_get_image_framework.c | 104 |
4 files changed, 128 insertions, 0 deletions
diff --git a/include/perk/perk.h b/include/perk/perk.h index 8c6711e..02d3275 100644 --- a/include/perk/perk.h +++ b/include/perk/perk.h @@ -154,6 +154,10 @@ struct pe_unit_ctx { void * any; }; +struct pe_info_string { + char buffer[128]; +}; + /* package info */ perk_api const struct pe_source_version * pe_source_version(void); @@ -188,6 +192,9 @@ perk_api int pe_get_rva_from_roffset (const struct pe_image_meta *, uint32_t ro perk_api int pe_get_expsym_by_name (const struct pe_image_meta *, const char * name, struct pe_expsym * optional); perk_api int pe_get_expsym_by_index (const struct pe_image_meta *, unsigned index, struct pe_expsym * optional); +/* info api */ +perk_api int pe_get_image_framework (const struct pe_image_meta *, struct pe_info_string * optional); + /* low-level api */ perk_api int pe_read_dos_header (const struct pe_image_dos_hdr *, struct pe_meta_image_dos_hdr *); perk_api int pe_read_coff_header (const struct pe_coff_file_hdr *, struct pe_meta_coff_file_hdr *); diff --git a/include/perk/perk_meta.h b/include/perk/perk_meta.h index e3dfab7..fc8c268 100644 --- a/include/perk/perk_meta.h +++ b/include/perk/perk_meta.h @@ -7,6 +7,22 @@ extern "C" { #include <stdint.h> +enum pe_framework { + PE_FRAMEWORK_UNKNOWN, + PE_FRAMEWORK_FREESTD, + PE_FRAMEWORK_PSXSCL, + PE_FRAMEWORK_MIDIPIX, + PE_FRAMEWORK_CYGONE, + PE_FRAMEWORK_CYGWIN, + PE_FRAMEWORK_MINGW, + PE_FRAMEWORK_MSYS, + PE_FRAMEWORK_SUACON, + PE_FRAMEWORK_WINCON, + PE_FRAMEWORK_WINCLI, + PE_FRAMEWORK_WIN32, + PE_FRAMEWORK_CAP +}; + /* generic block info / image directory header */ struct pe_block { uint32_t rva; diff --git a/project/common.mk b/project/common.mk index 453a374..b71e972 100644 --- a/project/common.mk +++ b/project/common.mk @@ -2,6 +2,7 @@ API_SRCS = \ src/driver/pe_amain.c \ src/driver/pe_driver_ctx.c \ src/driver/pe_unit_ctx.c \ + src/logic/pe_get_image_framework.c \ src/logic/pe_get_image_meta.c \ src/logic/pe_map_raw_image.c \ src/output/pe_output_error.c \ diff --git a/src/logic/pe_get_image_framework.c b/src/logic/pe_get_image_framework.c new file mode 100644 index 0000000..ba44d2f --- /dev/null +++ b/src/logic/pe_get_image_framework.c @@ -0,0 +1,104 @@ +/***************************************************************/ +/* perk: PE Resource Kit */ +/* Copyright (C) 2015--2016 Z. Gilboa */ +/* Released under GPLv2 and GPLv3; see COPYING.PERK. */ +/***************************************************************/ + +#include <string.h> +#include <stdbool.h> + +#include <perk/perk.h> +#include <perk/perk_meta.h> + +static const char const * pe_framework_str[PE_FRAMEWORK_CAP] = { + [PE_FRAMEWORK_UNKNOWN] = "unknown", + [PE_FRAMEWORK_FREESTD] = "freestd", + [PE_FRAMEWORK_PSXSCL] = "psxscl", + [PE_FRAMEWORK_MIDIPIX] = "midipix", + [PE_FRAMEWORK_CYGONE] = "cygone", + [PE_FRAMEWORK_CYGWIN] = "cygwin", + [PE_FRAMEWORK_MINGW] = "mingw", + [PE_FRAMEWORK_MSYS] = "msys", + [PE_FRAMEWORK_SUACON] = "suacon", + [PE_FRAMEWORK_WINCON] = "wincon", + [PE_FRAMEWORK_WINCLI] = "wincli", + [PE_FRAMEWORK_WIN32] = "win32", +}; + +static bool pe_image_is_psxscl(const struct pe_image_meta * m) +{ + return (!m->summary.nimplibs + && !pe_get_expsym_by_name(m,"__psx_init",0)); +} + +static bool pe_image_is_cygwin(const struct pe_image_meta * m) +{ + int i; + + for (i=0; i<m->summary.nimplibs; i++) + if (!(strcmp(m->idata[i].name,"cygwin1.dll"))) + return true; + + return false; +} + +static bool pe_image_is_msys(const struct pe_image_meta * m) +{ + int i; + + for (i=0; i<m->summary.nimplibs; i++) + if (!(strcmp(m->idata[i].name,"msys-2.0.dll"))) + return true; + + return false; +} + +static bool pe_image_is_mingw(const struct pe_image_meta * m) +{ + return ((pe_get_named_section_index(m,".CRT") >= 0) + && (pe_get_named_section_index(m,".bss") >= 0) + && (pe_get_named_section_index(m,".tls") >= 0)); +} + +int pe_get_image_framework(const struct pe_image_meta * m, struct pe_info_string * infostr) +{ + int framework; + + if (pe_get_named_section_index(m,".midipix") >= 0) + framework = PE_FRAMEWORK_MIDIPIX; + + else if (pe_get_named_section_index(m,".freestd") >= 0) + framework = PE_FRAMEWORK_FREESTD; + + else if (pe_get_named_section_index(m,".cygheap") >= 0) + framework = PE_FRAMEWORK_CYGONE; + + else if (pe_image_is_psxscl(m)) + framework = PE_FRAMEWORK_PSXSCL; + + else if (pe_image_is_cygwin(m)) + framework = PE_FRAMEWORK_CYGWIN; + + else if (pe_image_is_msys(m)) + framework = PE_FRAMEWORK_MSYS; + + else if (pe_image_is_mingw(m)) + framework = PE_FRAMEWORK_MINGW; + + else if (m->opt.img.subsystem == PE_IMAGE_SUBSYSTEM_POSIX_CUI) + framework = PE_FRAMEWORK_SUACON; + + else if (m->opt.img.subsystem == PE_IMAGE_SUBSYSTEM_WINDOWS_CUI) + framework = PE_FRAMEWORK_WINCON; + + else if (m->opt.img.subsystem == PE_IMAGE_SUBSYSTEM_WINDOWS_GUI) + framework = PE_FRAMEWORK_WIN32; + + else + framework = PE_FRAMEWORK_UNKNOWN; + + if (infostr) + strcpy(infostr->buffer,pe_framework_str[framework]); + + return framework; +} |