summaryrefslogtreecommitdiff
path: root/plugins/elf/dynamic.c
diff options
context:
space:
mode:
Diffstat (limited to 'plugins/elf/dynamic.c')
-rw-r--r--plugins/elf/dynamic.c107
1 files changed, 107 insertions, 0 deletions
diff --git a/plugins/elf/dynamic.c b/plugins/elf/dynamic.c
index ed681d1..f1d5e02 100644
--- a/plugins/elf/dynamic.c
+++ b/plugins/elf/dynamic.c
@@ -111,6 +111,35 @@ bool find_elf_dynamic_item_from_pheader(const GElfFormat *format, const elf_phdr
/******************************************************************************
* *
+* Paramètres : format = informations chargées à consulter. *
+* type = sorte d'élément recherché. *
+* item = élément retrouvé dans la section. [OUT] *
+* *
+* Description : Retrouve rapidement un élément dans la section dynamique. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool find_elf_dynamic_item(const GElfFormat *format, int64_t type, elf_dyn *item)
+{
+ bool result; /* Bilan à retourner */
+ elf_phdr dynamic; /* En-tête de programme DYNAMIC*/
+
+ result = find_elf_dynamic_program_header(format, &dynamic);
+
+ if (result)
+ result = find_elf_dynamic_item_from_pheader(format, &dynamic, type, item);
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
* Paramètres : format = description de l'exécutable à consulter. *
* count = nombre d'éléments dans la liste constituée. *
* *
@@ -202,3 +231,81 @@ const char **list_elf_needed_objects(const GElfFormat *format, size_t *count)
return result;
}
+
+
+/******************************************************************************
+* *
+* Paramètres : format = description de l'exécutable à manipuler. *
+* virt = position en mémoire de la PLT. [OUT] *
+* *
+* Description : Retrouve l'adresse de la PLT en se basant sur la GOT. *
+* *
+* Retour : Bilan de l'opération. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+bool resolve_plt_using_got(GElfFormat *format, virt_t *virt)
+{
+ bool result; /* Bilan à retourner */
+ elf_phdr dynamic; /* Programme à analyser */
+ elf_dyn pltgot; /* Table de type DT_PLTGOT */
+ virt_t got_virt; /* Adresse mémoire de la GOT */
+ vmpa2t got_addr; /* Localisation complète */
+ GBinContent *content; /* Contenu binaire à parcourir */
+ uint32_t raw_32; /* Valeur brute de 32 bits lue */
+ uint64_t raw_64; /* Valeur brute de 64 bits lue */
+
+ result = false;
+
+ if (!find_elf_program_by_type(format, PT_DYNAMIC, &dynamic))
+ goto rpug_exit;
+
+ if (!find_elf_dynamic_item_from_pheader(format, &dynamic, DT_PLTGOT, &pltgot))
+ goto rpug_exit;
+
+ got_virt = ELF_DYN(format, pltgot, d_un.d_ptr);
+
+ if (!g_exe_format_translate_address_into_vmpa(G_EXE_FORMAT(format), got_virt, &got_addr))
+ goto rpug_exit;
+
+ content = G_BIN_FORMAT(format)->content;
+
+ /**
+ * Quelques pistes pour la connaissance des premières cellules d'une GOT :
+ *
+ * "Lazy procedure linkage with the PLT" (mot clef : GOT+4).
+ * http://www.iecc.com/linker/linker10.html
+ *
+ * "How the ELF Ruined Christmas" (mot clef : GOT[1]).
+ * https://www.usenix.org/system/files/conference/usenixsecurity15/sec15-paper-di-frederico.pdf
+ */
+
+ if (format->is_32b)
+ {
+ advance_vmpa(&got_addr, 3 * sizeof(uint32_t));
+
+ result = g_binary_content_read_u32(content, &got_addr, format->endian, &raw_32);
+
+ if (result)
+ *virt = raw_32;
+
+ }
+
+ else
+ {
+ advance_vmpa(&got_addr, 3 * sizeof(uint64_t));
+
+ result = g_binary_content_read_u64(content, &got_addr, format->endian, &raw_64);
+
+ if (result)
+ *virt = raw_64;
+
+ }
+
+ rpug_exit:
+
+ return result;
+
+}