diff options
-rw-r--r-- | plugins/dex/dex-int.c | 63 |
1 files changed, 61 insertions, 2 deletions
diff --git a/plugins/dex/dex-int.c b/plugins/dex/dex-int.c index 287ec7a..843db32 100644 --- a/plugins/dex/dex-int.c +++ b/plugins/dex/dex-int.c @@ -32,6 +32,7 @@ #include <common/endianness.h> +#include <common/utf8.h> #include <plugins/dalvik/pseudo/identifiers.h> @@ -160,6 +161,14 @@ bool read_dex_string_data_item(const GDexFormat *format, vmpa2t *pos, vmpa2t *in { bool result; /* Bilan à retourner */ GBinContent *content; /* Contenu binaire à lire */ + size_t consumed; /* Taille effective des données*/ + phys_t fullsize; /* Taille complète du contenu */ + vmpa2t old; /* Sauvegarde de position */ + uleb128_t i; /* Boucle de parcours */ + phys_t maxsize; /* Taille maximale d'une unité */ + const bin_t *tmp; /* Zone de parcours temporaire */ + size_t used; /* Quantié d'octets consommés */ + unichar_t ch; /* Unité de code MUTF-8 */ content = G_BIN_FORMAT(format)->content; @@ -170,8 +179,58 @@ bool read_dex_string_data_item(const GDexFormat *format, vmpa2t *pos, vmpa2t *in if (inter != NULL) copy_vmpa(inter, pos); - str_data->data = g_binary_content_get_raw_access(content, pos, str_data->utf16_size); - result = (str_data->data != NULL); + consumed = 0; + + fullsize = g_binary_content_compute_size(content); + + copy_vmpa(&old, pos); + + for (i = 0; i < (str_data->utf16_size + 1) && result; i++) + { + if (i > 0) + { + copy_vmpa(pos, &old); + advance_vmpa(pos, consumed); + } + + /** + * Théoriquement, les 4 octets maximaux pour l'encodage ne sont pas + * forcément tous disponibles... + * + * Il est alors possible d'obtenir une erreur pour un caractère + * légitime d'un octet. + * + * On borne donc la taille de la prochaine unité MUTF-8. + */ + + maxsize = fullsize - get_phy_addr(pos); + + if (maxsize > 4) + maxsize = 4; + + tmp = g_binary_content_get_raw_access(content, pos, maxsize); + + ch = decode_utf8_char(tmp, maxsize, &used); + + if (IS_UTF8_ERROR(ch)) + result = false; + + else + consumed += used; + + if (i == str_data->utf16_size) + result = (ch == 0x0); + + } + + copy_vmpa(pos, &old); + + if (result) + { + str_data->data = g_binary_content_get_raw_access(content, pos, consumed); + result = (str_data->data != NULL); + } + } return result; |