Implement CRC calculation of input sections
This commit is contained in:
parent
57be15d909
commit
c8da6e4f4c
@ -20,6 +20,7 @@ struct elf_section {
|
||||
struct elfpatch {
|
||||
uint32_t magic;
|
||||
int fd;
|
||||
bool readonly;
|
||||
Elf *elf;
|
||||
GElf_Ehdr ehdr;
|
||||
int class;
|
||||
@ -218,7 +219,7 @@ static int elf_patch_update_info(elfpatch_handle_t *ep)
|
||||
return 0;
|
||||
}
|
||||
|
||||
elfpatch_handle_t *elf_patch_open(const char *path)
|
||||
elfpatch_handle_t *elf_patch_open(const char *path, bool readonly)
|
||||
{
|
||||
struct elfpatch *ep;
|
||||
|
||||
@ -229,13 +230,14 @@ elfpatch_handle_t *elf_patch_open(const char *path)
|
||||
|
||||
ep = (struct elfpatch *)calloc(1u, sizeof(struct elfpatch));
|
||||
ep->magic = ELFPATCH_MAGIC;
|
||||
ep->readonly = readonly;
|
||||
|
||||
ep->fd = open(path, O_RDWR, 0);
|
||||
ep->fd = open(path, readonly ? O_RDONLY : O_RDWR, 0);
|
||||
if (ep->fd < 0) {
|
||||
print_err("Error opening file: %s\n", path);
|
||||
goto free_struct;
|
||||
}
|
||||
ep->elf = elf_begin(ep->fd, ELF_C_RDWR, NULL);
|
||||
ep->elf = elf_begin(ep->fd, readonly ? ELF_C_READ : ELF_C_RDWR, NULL);
|
||||
if (!ep->elf) {
|
||||
print_err("[LIBELF] %s\n", elf_errmsg(-1));
|
||||
goto close_fd;
|
||||
|
@ -14,7 +14,7 @@ enum granularity {
|
||||
};
|
||||
|
||||
|
||||
elfpatch_handle_t *elf_patch_open(const char *path);
|
||||
elfpatch_handle_t *elf_patch_open(const char *path, bool readonly);
|
||||
|
||||
/**
|
||||
* @brief Check if a section is present in file
|
||||
|
122
main.c
122
main.c
@ -27,6 +27,7 @@
|
||||
#include <linklist-lib/singly-linked-list.h>
|
||||
#include <patchelfcrc/reporting.h>
|
||||
#include <patchelfcrc/elfpatch.h>
|
||||
#include <fort.h>
|
||||
|
||||
const char *argp_program_bug_address = "<mario [dot] huettel [at] linux [dot] com>";
|
||||
|
||||
@ -232,11 +233,101 @@ static void free_cmd_args(struct command_line_options *opts)
|
||||
opts->section_list = NULL;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief check_all_sections_present
|
||||
* @param ep
|
||||
* @param list
|
||||
* @return -1 if no sections are provided. 0 if all sections are present. -2 if setions cannot be found
|
||||
*/
|
||||
static int check_all_sections_present(elfpatch_handle_t *ep, SlList *list)
|
||||
{
|
||||
SlList *iter;
|
||||
const char *sec_name;
|
||||
int ret = 0;
|
||||
|
||||
if (!ep)
|
||||
return -1001;
|
||||
if (!list) {
|
||||
print_err("No input sections specified.\n")
|
||||
return -1;
|
||||
}
|
||||
for (iter = list; iter; iter = sl_list_next(iter)) {
|
||||
sec_name = (const char *)iter->data;
|
||||
if (!sec_name)
|
||||
continue;
|
||||
if (elf_patch_check_for_section(ep, sec_name)) {
|
||||
print_err("Cannot find section '%s'\n", sec_name);
|
||||
ret = -2;
|
||||
} else {
|
||||
print_debug("Input section '%s': found\n", sec_name);
|
||||
}
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Compute CRCs over the sections in @p list
|
||||
* @param ep Elf patch
|
||||
* @param list List of section names to patch
|
||||
* @param opts Command line options. Used for CRC generation
|
||||
* @param[out] crcs Array of output CRCs. Must be large enough to hold all elements
|
||||
* @return 0 if successful
|
||||
*/
|
||||
static int compute_crcs(elfpatch_handle_t *ep, SlList *list, const struct command_line_options *opts, uint32_t *crcs)
|
||||
{
|
||||
SlList *iter;
|
||||
const char *sec_name;
|
||||
int ret = 0;
|
||||
struct crc_calc _crc;
|
||||
struct crc_calc * const crc = &_crc;
|
||||
unsigned int idx;
|
||||
|
||||
/* Construct the CRC */
|
||||
crc_init(crc, &opts->crc);
|
||||
|
||||
for (iter = list, idx = 0; iter; iter = sl_list_next(iter), idx++) {
|
||||
crc_reset(crc);
|
||||
sec_name = (const char *)iter->data;
|
||||
if (elf_patch_compute_crc_over_section(ep, sec_name, crc, opts->granularity, opts->little_endian)) {
|
||||
print_err("Error during CRC calculation. Exiting.\n");
|
||||
ret = -1;
|
||||
break;
|
||||
}
|
||||
crc_finish_calc(crc);
|
||||
crcs[idx] = crc_get_value(crc);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void print_crcs(SlList *list, const uint32_t *crcs)
|
||||
{
|
||||
SlList *iter;
|
||||
unsigned int idx;
|
||||
const char *sec_name;
|
||||
ft_table_t *table;
|
||||
|
||||
table = ft_create_table();
|
||||
|
||||
/* Write header */
|
||||
ft_set_cell_prop(table, 0, FT_ANY_COLUMN, FT_CPROP_ROW_TYPE, FT_ROW_HEADER);
|
||||
ft_write_ln(table, "Section", "CRC");
|
||||
|
||||
for (iter = list, idx = 0; iter; iter = sl_list_next(iter), idx++) {
|
||||
sec_name = (const char *)iter->data;
|
||||
ft_printf_ln(table, "%s|0x%x", sec_name, crcs[idx]);
|
||||
}
|
||||
print_debug("Calculated CRCs:\n%s\n", ft_to_string(table));
|
||||
ft_destroy_table(table);
|
||||
}
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
struct crc_calc crc;
|
||||
struct command_line_options cmd_opts;
|
||||
elfpatch_handle_t *ep;
|
||||
int ret = 0;
|
||||
uint32_t *crcs;
|
||||
|
||||
prepare_default_opts(&cmd_opts);
|
||||
parse_cmdline_options(&argc, &argv, &cmd_opts);
|
||||
@ -262,26 +353,35 @@ int main(int argc, char **argv)
|
||||
goto free_cmds;
|
||||
}
|
||||
|
||||
/* Build the CRC */
|
||||
crc_init(&crc, &cmd_opts.crc);
|
||||
|
||||
/* Prepare libelf for use with the latest ELF version */
|
||||
elf_version(EV_CURRENT);
|
||||
|
||||
/* Open the ELF file */
|
||||
ep = elf_patch_open(cmd_opts.elf_path);
|
||||
ep = elf_patch_open(cmd_opts.elf_path, cmd_opts.dry_run);
|
||||
if (!ep) {
|
||||
ret = -2;
|
||||
goto free_cmds;
|
||||
}
|
||||
|
||||
/* TODO: Implement this correctly! */
|
||||
elf_patch_compute_crc_over_section(ep, ".text", &crc, cmd_opts.granularity, cmd_opts.little_endian);
|
||||
/* Check if all sections are present */
|
||||
if (check_all_sections_present(ep, cmd_opts.section_list)) {
|
||||
ret = -2;
|
||||
goto free_cmds;
|
||||
}
|
||||
|
||||
/* Compute CRCs over sections */
|
||||
crcs = (uint32_t *)malloc(sl_list_length(cmd_opts.section_list) * sizeof(uint32_t));
|
||||
compute_crcs(ep, cmd_opts.section_list, &cmd_opts, crcs);
|
||||
|
||||
if (reporting_get_verbosity()) {
|
||||
print_crcs(cmd_opts.section_list, crcs);
|
||||
}
|
||||
|
||||
elf_patch_close_and_free(ep);
|
||||
|
||||
printf("CRC is: 0x%08x\n", crc_get_value(&crc));
|
||||
|
||||
crc_destroy(&crc);
|
||||
free_cmds:
|
||||
|
||||
free_cmd_args(&cmd_opts);
|
||||
|
||||
return 0;
|
||||
return ret;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user