Rappel de l’énoncé
Dans votre nouveau laboratoire, vous trouvez un micro-onde appelé Louis et une cafetière nommée Rachèle qui vous semblent être tout à fait sympathiques. Selon les employés du labo, ils sont capables d’émettre quand ils ont fini. En les regardant de plus près, vous remarquez que des capteurs de température leur sont accolés. Les étiquettes de ces capteurs contiennent des termes que vous ne comprenez pas dont une mention liée à une fréquence, LoRa : 433.242 MHz. Vous sortez vos outils de capture de signal que vous avez sous la main. Vous extrayez un fichier en prenant une fréquence de capture de 1 MHz.
Les capteurs n’ont pas l’air d’être neufs et leur aspect vous fait penser que certaines données ont été corrompues mais le vieux briscard du labo vous assure que la correction se fait toute seule et que le message est tout à fait compréhensible.
Un fichier au format IQ nous est fourni par la suite.
Premières analyses (Inspectrum)
Nous commencons par analyser le fichier via le logiciel inspectrum (n’hésitez pas à zoomer):
Nous retrouvons ici plusieurs suites de signaux, à un offset (positif et négatif) d’environ 270kHz à partir de 0. N’ayant jamais vu ce type de données auparavant, nous entamons la lecture de documentation sur LoRa, la technologie mentionnée dans l’énoncé.
Voilà plusieurs sources très intéressantes, qui ont permis une mise à niveau et une meilleure compréhension :
https://revspace.nl/DecodingLora
https://www.youtube.com/watch?v=-YNMRZC6v1s, https://www.youtube.com/watch?v=NoquBA7IMNc (présentations de Matt Knight sur le protocole ainsi qu’un projet gnuradio)
Nous n’allons pas détailler le fonctionnement du protocole, le premier lien cité plus haut résume parfaitement ce qu’il y a à comprendre et nous vous invitons à le consulter. Le formatage n’est pas compliqué à assimiler, mais le décodage à la main avec inspectrum risque d’être impossible, long et imprécis.
Le logiciel gnuradio est alors tout indiqué, car il dispose de toutes les fonctionnalités d’analyse du signal nécessaires. N’ayant pas spécialement envie d’implémenter toute la chaîne à la main, nous nous mettons à la recherche d’un projet GitHub.
Tentatives de décodage via gr-lora_sdr
gr-lora de rpp0 est un OOT (Out Of Tree modules) implémentant des blocs gnuradio spécifiques au décodage de LoRa. Nous l’installons donc avec la dernière version de gnuradio (3.10.2.0 ), et tentons de décoder le fichier IQ, en modifiant certains paramètres :
Ici, nous choisissons un sample rate de 1MHz, qui est la valeur par défaut et n’a pas besoin d’être modifiée, un centrage en fréquence de 0 (nous n’utilisons pas d’antenne), une “Bandwidth” de 250kHz et un “Spreading Factor” (nombre de bits par symbole) de 7. Pourquoi ces deux dernières valeurs ? En voilà l’explication :
source : dautrylimoges.scenari-community.org
Nous avons pu voir dans inspectrum une largeur de bande d’environ 250 kHz, ce qui implique alors un SF de 7. Néanmoins, nous allons voir que cette implication n’était pas forcément vraie.
Le bloc de décodage ne trouve rien du tout, et la présence d’erreurs (indiqué dans l’énoncé) me fait penser qu’il va falloir être en possession de toute la chaîne de décodage. Il est l’heure de chercher un autre projet GitHub.
Décodage d’un morceau du flag via gr-lora_sdr
gr-lora_sdr de tapparelj implémente toute la chaîne de blocs permettant le décodage de LoRa. C’est donc le candidat parfait pour essayer de modifier spécifiquement certaines valeurs et rentrer dans les détails. Nous décidons de l’installer.
Nous omettons volontairement la partie où il a été nécessaire de créer une seconde VM pour installer gnuradio 3.8, car cet OOT ne semblait pas vouloir fonctionner avec la dernière version de gnuradio :)
Le repo GitHub contient un exemple de schéma de décodage, que nous nous empressons de reproduire à l’identique :
Afin de gagner du temps nous déclarons quelques variables pour les tests à venir, puis nous exécutons en modifiant simplement BW et SF :
Miracle ! Le flag Une partie du flag s’affiche sous nos yeux ! Nous remarquons instantanément la double répétition du message suivie d’une indication d’en-tête. Cela correspond aux trois bandes à l’offset positif visibles sur la capture inspectrum. Il ne nous reste plus qu’à comprendre pourquoi la bande en négatif n’est pas détectée.
Correction d’erreur et seconde partie du flag
Nous retournons sur inspectrum et tentons de situer l’erreur :
En repensant à un certain passage lue dans la documentation plus haut, cela nous apparaît comme une évidence :
[…]On the air I have seen the following waveforms:
a series of up-chirps at the start of a message (preamble), the number of up-chirps corresponds to the PreambleLength registers[…]
Ce signal LoRa est en effet inversé, si vous regardez la première capture inspectrum, vous pouvez voir que les trois blocs du hauts commencent par des chirps (sauts en fréquence) positifs. Le schéma est donc le même, mais tous les chirps sont inversés.
Après une dizaine de minute à imaginer des plans bien trop complexes pour inverser ces chirps, nous nous rappelons que nous avons affaire à un fichier IQ, et que l’inversion de ces deux composants devrait suffire !
Le bloc “swap iq” de gnuradio n’est apparu qu’en version 3.9, il a fallu retourner sur le premier schéma gr-lora_sdr pour réaliser cette opération
Voyons le résultat dans inspectrum :
Hourra ! Les deux bandes ont changé de place, et les chirps sont désormais dans le bon sens (ou le mauvais pour les trois bandes désormais en offset négatif).
Nous changeons de fichier source sur le schéma gnuradio, et décodons … rien du tout. En effet, nous pouvons voir que le nombre de chirps par seconde (l’axe X de inspectrum représente le temps) est beaucoup plus élevé pour les signaux de la première partie du flag que dans la seconde.
Néanmoins, la largeur de bande est de 250kHz, ce qui implique forcément un SF de 7 ? Et bien, visiblement, Louis le micro-onde ou Rachèle la cafetière nous a induit en erreur et a décidé d’ignorer le tableau de correspondance plus haut.
La bonne réponse était … bruteforcer le SF :
Cela fait sens au niveau de la durée des chirps, mais pas de la largeur de bande. Soit nous avons manqué quelque chose (bien que tous les tableaux sur le web confirmaient qu’une BW de 250kHz associait forcément un SF de 7), soit cela faisait partie de l’épreuve (la seconde option est à privilégier :) )
Conclusion
Challenge particulièrement intéressant et difficile lorsque l’on ne connaît pas LoRa, qui nous a permis de nous confronter à de la télécom’ assez sympa et peu ordinaire en CTF.
Flag : FCSC{0083fa85206b09970d550b9e8ba8a705be62027e6e769d6ed5e87b8e93dd5759}