Solution de bluesheet pour Le Rustique

misc

17 novembre 2023

Table des matières

Le Rustique

200 points

Enoncé

On vous demande d’auditer cette solution de vérification syntaxique en Rust.

Ma solution

On ne dispose que de l’information suivante : le programme a-t-il compilé ?

Ainsi, la seule chose que je peux exploiter est l’ensemble de fonctions de type const fn de Rust, qui s’exécutent au moment de la compilation (et qui peuvent par conséquent provoquer des erreurs de compilation)

On utilise dans un premier temps la macro std::include_str!, qui inclut un fichier sous forme de chaine de caractère au moment de la compilation. Ceci peut me permettre de localiser le flag, par guessing. En effet, après quelques tentatives infructueuses, je trouve un fichier flag.txt dans le répertoire parent. Coup de chance, on prend :)

Maintenant, on peut essayer de faire une attaque blind sur le contenu de cette chaine de caractères : L’idée, c’est de faire crash la compilation en assignant à un entier unsigned une valeur négative. Le payload final pour la dichotomie caractère par caractère:

fn main() {
    const WHATEVER: u8 = std::include_str!("../flag.txt").as_bytes()[$c] - $val - 1;
}

$c est l’indice du caractère sur lequel on effectue la dichotomie, et $val la valeur de comparaison.

Ce code va compiler si et seulement si l’octet d’indice $c est plus grand (strictement) que $val.

Je fais un petit script python pour automatiser tout ça, et on obtient le flag !