Beginning to disassemble files again
This commit is contained in:
parent
c0a0820fe4
commit
383ca51178
@ -41,6 +41,7 @@ char const * as_get_format_name(As * as);
|
||||
|
||||
/* useful */
|
||||
int as_decode(As * as, char const * buffer, size_t size);
|
||||
int as_decode_file(As * as, char const * filename, FILE * fp);
|
||||
int as_parse(As * as, char const * infile, char const * outfile);
|
||||
|
||||
int as_open(As * as, char const * outfile);
|
||||
|
35
src/arch.c
35
src/arch.c
@ -63,6 +63,7 @@ struct _Arch
|
||||
/* prototypes */
|
||||
/* callbacks */
|
||||
static char const * _arch_get_filename(Arch * arch);
|
||||
static ssize_t _arch_read(Arch * arch, void * buf, size_t size);
|
||||
static ssize_t _arch_read_buffer(Arch * arch, void * buf, size_t size);
|
||||
static ssize_t _arch_write(Arch * arch, void const * buf, size_t size);
|
||||
|
||||
@ -489,6 +490,23 @@ static void _decode_print(ArchInstructionCall * call)
|
||||
}
|
||||
|
||||
|
||||
/* arch_decode_at */
|
||||
int arch_decode_at(Arch * arch, off_t offset, size_t size, off_t base)
|
||||
{
|
||||
int ret;
|
||||
|
||||
if(arch->fp == NULL)
|
||||
return -error_set_code(1, "%s", strerror(ENOSYS));
|
||||
if(fseek(arch->fp, offset, SEEK_SET) != 0)
|
||||
return -error_set_code(1, "%s", strerror(errno));
|
||||
/* FIXME implement size, consider offset and base */
|
||||
if((ret = arch_decode(arch)) == 0
|
||||
&& fseek(arch->fp, offset + size, SEEK_SET) != 0)
|
||||
ret = -error_set_code(1, "%s", strerror(errno));
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
/* arch_exit */
|
||||
int arch_exit(Arch * arch)
|
||||
{
|
||||
@ -519,7 +537,7 @@ int arch_init(Arch * arch, char const * filename, FILE * fp)
|
||||
arch->helper.get_instruction_by_opcode = arch_get_instruction_by_opcode;
|
||||
arch->helper.get_register_by_id_size = arch_get_register_by_id_size;
|
||||
arch->helper.get_register_by_name_size = arch_get_register_by_name_size;
|
||||
arch->helper.read = NULL;
|
||||
arch->helper.read = _arch_read;
|
||||
arch->helper.write = _arch_write;
|
||||
arch->plugin->helper = &arch->helper;
|
||||
return 0;
|
||||
@ -568,6 +586,21 @@ static char const * _arch_get_filename(Arch * arch)
|
||||
}
|
||||
|
||||
|
||||
/* arch_read */
|
||||
static ssize_t _arch_read(Arch * arch, void * buf, size_t size)
|
||||
{
|
||||
if(fread(buf, size, 1, arch->fp) == 1)
|
||||
return size;
|
||||
if(ferror(arch->fp))
|
||||
return -error_set_code(1, "%s: %s", arch->filename,
|
||||
strerror(errno));
|
||||
if(feof(arch->fp))
|
||||
return -error_set_code(1, "%s: %s", arch->filename,
|
||||
"End of file reached");
|
||||
return -error_set_code(1, "%s: %s", arch->filename, "Read error");
|
||||
}
|
||||
|
||||
|
||||
/* arch_read_buffer */
|
||||
static ssize_t _arch_read_buffer(Arch * arch, void * buf, size_t size)
|
||||
{
|
||||
|
@ -60,5 +60,6 @@ int arch_write(Arch * arch, ArchInstruction * instruction,
|
||||
|
||||
/* disassembly */
|
||||
int arch_decode(Arch * arch);
|
||||
int arch_decode_at(Arch * arch, off_t offset, size_t size, off_t base);
|
||||
|
||||
#endif /* !ASM_ARCH_H */
|
||||
|
15
src/asm.c
15
src/asm.c
@ -154,6 +154,21 @@ int as_decode(As * as, char const * buffer, size_t size)
|
||||
}
|
||||
|
||||
|
||||
/* as_decode_file */
|
||||
int as_decode_file(As * as, char const * filename, FILE * fp)
|
||||
{
|
||||
int ret;
|
||||
|
||||
if(fp != NULL)
|
||||
return code_decode_file(as->code, filename, fp);
|
||||
if((fp = fopen(filename, "r")) == NULL)
|
||||
return -error_set_code(1, "%s: %s", filename, strerror(errno));
|
||||
ret = code_decode_file(as->code, filename, fp);
|
||||
fclose(fp);
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
/* as_parse */
|
||||
int as_parse(As * as, char const * infile, char const * outfile)
|
||||
{
|
||||
|
29
src/code.c
29
src/code.c
@ -137,6 +137,35 @@ int code_decode(Code * code, char const * buffer, size_t size)
|
||||
arch_exit(code->arch);
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
/* code_decode_file */
|
||||
static int _decode_file_callback(void * priv, char const * section,
|
||||
off_t offset, size_t size, off_t base);
|
||||
|
||||
int code_decode_file(Code * code, char const * filename, FILE * fp)
|
||||
{
|
||||
int ret;
|
||||
|
||||
arch_init(code->arch, filename, fp);
|
||||
format_init(code->format, filename, fp);
|
||||
ret = format_decode(code->format, _decode_file_callback, code);
|
||||
format_exit(code->format);
|
||||
arch_exit(code->arch);
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int _decode_file_callback(void * priv, char const * section,
|
||||
off_t offset, size_t size, off_t base)
|
||||
{
|
||||
Code * code = priv;
|
||||
|
||||
if(section != NULL)
|
||||
printf("%s%s:\n", "\nDisassembly of section ", section);
|
||||
return arch_decode_at(code->arch, offset, size, base);
|
||||
}
|
||||
|
||||
|
||||
#if 0
|
||||
static ArchInstruction * _decode_size(Code * code, size_t * size,
|
||||
ArchInstruction * ai);
|
||||
|
@ -50,5 +50,6 @@ int code_section(Code * code, char const * section);
|
||||
|
||||
/* disassembly */
|
||||
int code_decode(Code * code, char const * buffer, size_t size);
|
||||
int code_decode_file(Code * code, char const * filename, FILE * fp);
|
||||
|
||||
#endif /* !ASM_CODE_H */
|
||||
|
14
src/deasm.c
14
src/deasm.c
@ -53,7 +53,6 @@ typedef struct _DeasmFormat
|
||||
typedef struct _Deasm
|
||||
{
|
||||
char const * arch;
|
||||
As * as;
|
||||
|
||||
FormatPluginHelper helper;
|
||||
DeasmFormat * format;
|
||||
@ -108,7 +107,6 @@ static int _deasm(char const * arch, char const * format,
|
||||
Deasm deasm;
|
||||
|
||||
deasm.arch = arch;
|
||||
deasm.as = NULL;
|
||||
deasm.helper.format = &deasm;
|
||||
deasm.helper.read = _deasm_helper_read;
|
||||
deasm.helper.seek = _deasm_helper_seek;
|
||||
@ -123,8 +121,6 @@ static int _deasm(char const * arch, char const * format,
|
||||
ret = _deasm_do_format(&deasm, format);
|
||||
else
|
||||
ret = _deasm_do(&deasm);
|
||||
if(deasm.as != NULL)
|
||||
as_delete(deasm.as);
|
||||
fclose(deasm.fp);
|
||||
_deasm_format_close_all(&deasm);
|
||||
if(ret != 0)
|
||||
@ -205,6 +201,7 @@ static int _deasm_do(Deasm * deasm)
|
||||
static int _deasm_do_callback(Deasm * deasm, FormatPlugin * format)
|
||||
{
|
||||
int ret;
|
||||
As * as;
|
||||
|
||||
#ifdef DEBUG
|
||||
fprintf(stderr, "DEBUG: %s(\"%s\")\n", __func__, format->name);
|
||||
@ -217,11 +214,12 @@ static int _deasm_do_callback(Deasm * deasm, FormatPlugin * format)
|
||||
if((deasm->arch = format->detect(format)) == NULL)
|
||||
return -1;
|
||||
}
|
||||
if((deasm->as = as_new(deasm->arch, format->name)) == NULL)
|
||||
if((as = as_new(deasm->arch, format->name)) == NULL)
|
||||
return -error_print("deasm");
|
||||
printf("\n%s: %s-%s\n", deasm->filename, format->name,
|
||||
as_get_arch_name(deasm->as));
|
||||
ret = format->decode(format);
|
||||
printf("\n%s: %s-%s\n", deasm->filename, format->name, as_get_arch_name(
|
||||
as));
|
||||
ret = as_decode_file(as, deasm->filename, deasm->fp);
|
||||
as_delete(as);
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
38
src/format.c
38
src/format.c
@ -39,6 +39,11 @@ struct _Format
|
||||
/* file */
|
||||
char const * filename;
|
||||
FILE * fp;
|
||||
|
||||
/* diassembly */
|
||||
int (*decode_callback)(void * priv, char const * section, off_t offset,
|
||||
size_t size, off_t base);
|
||||
void * decode_priv;
|
||||
};
|
||||
|
||||
|
||||
@ -105,6 +110,37 @@ char const * format_get_name(Format * format)
|
||||
|
||||
|
||||
/* useful */
|
||||
/* format_decode */
|
||||
static int _decode_callback(Format * format, char const * section,
|
||||
off_t offset, size_t size, off_t base);
|
||||
|
||||
int format_decode(Format * format, int (*callback)(void * priv,
|
||||
char const * section, off_t offset, size_t size,
|
||||
off_t base), void * priv)
|
||||
{
|
||||
int ret;
|
||||
|
||||
if(format->plugin->decode == NULL)
|
||||
return error_set_code(1, "%s: %s", format_get_name(format),
|
||||
"Disassembly is not supported");
|
||||
format->helper.decode = _decode_callback;
|
||||
format->decode_callback = callback;
|
||||
format->decode_priv = priv;
|
||||
ret = format->plugin->decode(format->plugin);
|
||||
format->decode_callback = NULL;
|
||||
format->decode_priv = NULL;
|
||||
format->helper.decode = NULL;
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int _decode_callback(Format * format, char const * section,
|
||||
off_t offset, size_t size, off_t base)
|
||||
{
|
||||
return format->decode_callback(format->decode_priv, section, offset,
|
||||
size, base);
|
||||
}
|
||||
|
||||
|
||||
/* format_exit */
|
||||
int format_exit(Format * format)
|
||||
{
|
||||
@ -116,6 +152,7 @@ int format_exit(Format * format)
|
||||
if(format->plugin->exit != NULL)
|
||||
ret = format->plugin->exit(format->plugin);
|
||||
format->helper.format = NULL;
|
||||
format->helper.decode = NULL;
|
||||
format->helper.read = NULL;
|
||||
format->helper.seek = NULL;
|
||||
format->plugin->helper = NULL;
|
||||
@ -144,6 +181,7 @@ int format_init(Format * format, char const * filename, FILE * fp)
|
||||
format->filename = filename;
|
||||
format->fp = fp;
|
||||
format->helper.format = format;
|
||||
format->helper.decode = NULL;
|
||||
format->helper.get_filename = _format_get_filename;
|
||||
format->helper.read = _format_read;
|
||||
format->helper.seek = _format_seek;
|
||||
|
@ -38,4 +38,9 @@ int format_exit(Format * format);
|
||||
int format_function(Format * format, char const * function);
|
||||
int format_section(Format * format, char const * section);
|
||||
|
||||
/* disassembly */
|
||||
int format_decode(Format * format, int (*callback)(void * priv,
|
||||
char const * section, off_t offset, size_t size,
|
||||
off_t base), void * priv);
|
||||
|
||||
#endif /* !ASM_FORMAT_H */
|
||||
|
Loading…
Reference in New Issue
Block a user