2 points par GN⁺ 2023-08-24 | 1 commentaires | Partager sur WhatsApp
  • Application de bureau basée sur Electron, Discord fonctionne en interne comme une fenêtre Chromium, ce qui permet d’ouvrir les outils de développement web et, via eux, de modifier le code côté client
  • Certains clients moddés et plugins déverrouillent côté client une partie des fonctionnalités normalement réservées à l’abonnement payant Nitro
  • Le principe clé consiste à injecter des modules découpés par le code splitting de Webpack dans la variable webpackChunkdiscord_app afin d’explorer et remplacer des fonctions internes
  • La fonction de vérification de la qualité du partage d’écran n’est validée que côté client, ce qui permet son contournement, tandis que les thèmes premium sont en plus soumis à une vérification synchronisée côté serveur
  • Toutes les techniques montrées constituent une violation des conditions d’utilisation de Discord et comportent un risque de suspension de compte ainsi qu’un risque de compromission lié à l’exécution de code non vérifié

Vue d’ensemble

  • Il existe de nombreux clients Discord moddés qui modifient l’apparence ou ajoutent des fonctionnalités, et certains plugins déverrouillent même des fonctions nécessitant normalement un abonnement payant à Nitro
  • Le texte explique le principe technique qui rend cela possible en analysant l’architecture du client

Activation des outils de développement

  • Discord est développé avec Electron, un framework permettant de créer des applications multiplateformes avec des technologies web, et se rapproche donc d’un site web exécuté dans un navigateur
  • Il s’agit fondamentalement d’une fenêtre Chromium, ce qui permet d’ouvrir les outils de développement, même s’ils sont désactivés par défaut
    • Cette restriction existe parce que de nombreux utilisateurs ont vu leur compte compromis après avoir collé des commandes malveillantes sous l’effet de manœuvres d’ingénierie sociale menées par des acteurs malveillants
  • Si l’on comprend les risques, il est possible de les activer en ajoutant la valeur true à DANGEROUS_ENABLE_DEVTOOLS_ONLY_ENABLE_IF_YOU_KNOW_WHAT_YOURE_DOING dans le fichier %appdata%/discord/settings.json
    • Il devient ensuite possible d’ouvrir la console de développement avec ctrl + shift + i

Patching des fonctions de Discord

  • Pour optimiser le chargement initial, le code est découpé en plusieurs chunks chargés en parallèle ou à la demande (lazy-loaded), via la fonctionnalité code splitting de Webpack
  • Tous les chunks chargés sont stockés dans la variable webpackChunkdiscord_app
  • Pour exécuter du code qui utilise les variables et fonctions de Discord, il faut injecter du code dans cette variable
    • a.c est un objet qui contient tous les modules ; chaque module est structuré sous la forme chunk_id, loaded, exports
    • exports contient les fonctions, objets et valeurs primitives exportés par le module
  • Il est possible de créer une fonction find qui parcourt plusieurs modules JavaScript pour rechercher puis appeler une fonction donnée
    • Exemple : rechercher puis appeler la fonction getCurrentUser()
  • En remplaçant une fonction d’origine par une autre, on peut modifier son comportement et donc changer directement le code exécuté

Déverrouillage du streaming haute qualité

  • À partir de ce point, le contenu enfreint clairement les conditions d’utilisation de Discord et peut entraîner une suspension de compte ; il faut donc en assumer le risque
  • Deux fonctions, canStreamMidQuality et canStreamHighQuality, qui vérifient le niveau d’abonnement de l’utilisateur, sont appelées juste avant l’écran de sélection de qualité du partage d’écran
    • Si l’on force le retour de ces deux fonctions à true, il devient possible de sélectionner un partage d’écran en résolution native à 60 FPS, même sans abonnement Nitro
  • Discord ne semble pas actuellement vérifier côté serveur si le flux envoyé respecte réellement les limitations imposées aux utilisateurs non abonnés
    • Cela dit, Discord n’utilise pas encore le chiffrement de bout en bout (End-to-End encryption), ce qui laisse une possibilité de détection
    • Selon le texte de référence, Discord inspecte déjà les contenus audio et vidéo des utilisateurs et pourrait à l’avenir ajouter une vérification côté serveur avant le partage d’écran

Déverrouillage des thèmes premium

  • Si l’on force à true la valeur de la fonction canUseClientThemes, qui indique si l’utilisateur peut utiliser les thèmes Nitro, le bouton de sélection des thèmes premium est déverrouillé
  • Cependant, le thème s’applique brièvement puis revient presque aussitôt au thème par défaut
    • Le client tente d’enregistrer le changement de thème, mais le serveur vérifie l’absence d’autorisation et réapplique le thème par défaut dès réception de la réponse
  • En patchant la fonction shouldSync pour qu’elle renvoie false lorsque la valeur est appearance, il est possible de conserver le changement de thème en bloquant uniquement la synchronisation des réglages d’apparence
  • Les thèmes sont gérés entièrement côté client, et il reste toujours possible de modifier directement le CSS ; il est donc difficile pour Discord d’empêcher cela

Conclusion

  • Il existe du code permettant d’appliquer facilement les manipulations présentées, mais il reste essentiel de faire preuve de prudence avant de modifier le client ou d’utiliser un client moddé
  • Discord peut suspendre à tout moment les comptes en infraction avec ses conditions d’utilisation, et l’exécution de code non vérifié ayant accès au compte est extrêmement risquée
    • Message encodé dans le texte : "Ne collez jamais dans la console de développement du code que vous ne comprenez pas — c’est la façon la plus simple de se faire voler son compte"

1 commentaires

 
GN⁺ 2023-08-24
Avis sur Hacker News
  • Je me dis qu’un simple blob encodé en base64 ajouté à la fin, qui active toutes les fonctionnalités quand on l’exécute, pourrait constituer un vecteur d’attaque assez facile.
    Je ne voulais pas dire que je soupçonnais l’auteur, et je viens de le décoder : je me suis fait avoir.

    • Pour ceux qui ont la flemme de lancer base64 --decode, voici le résultat :
      // Here's a cake if you thought about inspecting the code before executing it:
      let css = 'font-size: 36px; font-weight: bold; color: red';
      console.log("%cNEVER paste code you don't understand into the development console.", css);
      console.log("%cThis is the best way to compromise your account.", css);
  • « Actuellement, Discord ne semble pas vérifier côté serveur que le flux transmis respecte bien les critères des non-abonnés » : je me demande qui a pu penser que c’était une bonne implémentation.
    La validation côté client ressemble vraiment à une erreur de débutant.

    • C’était probablement moins « c’est une excellente implémentation » que « on corrigera quand quelqu’un trouvera comment la casser ».
      En plusieurs années d’utilisation de Discord, c’est la première fois que j’entends parler d’une tentative de contournement de la structure d’accès de Nitro ; si ce n’est pas répandu, je ne vois pas trop pourquoi ils s’en préoccuperaient.
    • Je ne comprends absolument pas pourquoi ils ont fait ça, vu que, de mon côté, je n’implémente que des fonctionnalités terminées, exactement sous leur forme finale souhaitée, puis je soumets la PR.
      À part ça, j’ai commencé ce mois-ci mon cinquième nouveau poste, et il semblerait que je ne m’entende décidément pas avec les chefs de projet.
    • Vu la facilité avec laquelle les gens, surtout les enfants, dépensent de l’argent aujourd’hui, ça peut suffire.
      Je me demande combien de personnes comprennent ce genre de hack tout en étant prêtes à payer Nitro. Il y a sans doute des milliers, voire des dizaines de milliers, d’utilisateurs de mods de clients Discord qui activent une partie ou la totalité des fonctionnalités Nitro, mais j’ai des doutes sur le chiffre d’affaires réel que bloquer cela générerait.
      Personnellement, si j’avais besoin ou envie de cette fonctionnalité, il serait beaucoup moins pénible de payer 10 dollars par mois. C’est préférable au fait de suivre en permanence des mods qui risquent de casser à chaque mise à jour de Discord, en espérant que le mainteneur n’y glisse pas de code malveillant.
    • Via l’API, on peut aussi voir le nom, le sujet et l’heure du dernier message de salons masqués.
      Les salons ne sont masqués que côté client. Pour être clair, cela ne permet toutefois pas de voir le contenu des messages de ces salons.
    • C’est parce que ce n’est pas un composant de l’API Discord, mais le côté serveurs vocaux, déployés par centaines dans le monde.
      Les serveurs vocaux vérifient seulement auprès de l’API que vous avez le droit d’entrer, puis se comportent ensuite comme un diffuseur de paquets un-vers-plusieurs.
  • C’est assez proche du hacker classique, au sens curieux et compétent du terme.
    Il n’y a pas de dommage grave, et cela rappelle que les apps ne sont pas magiques et que le code, c’est cool.

    • C’est peut-être plus proche d’un « cracker », mais je suis d’accord pour dire que c’est le genre de connaissances que les entreprises préféreraient que nous n’ayons pas.
      Comme ça, elles peuvent essayer de nous soutirer davantage d’argent sans résistance.
  • Rappelons encore une fois que tout ce que vous envoyez sur Discord, DM compris, est enregistré en clair chez Discord et devient accessible à Discord ainsi qu’à toute entité qui rachèterait l’entreprise.
    À un moment, Microsoft semblait sur le point de l’acheter, et maintenant ils semblent se diriger vers une IPO.
    Le simple fait d’avoir un compte normalise les conversations privées faciles à exploiter pour du data mining destiné à l’IA, ou par Discord et les administrateurs de ses bases de données/systèmes. La Section 702 du FISA Amendments Act (FAA702) permet aux agences fédérales d’enquête d’accéder à ces données sans mandat.
    Rien que la possibilité de faire du front-running sur les cryptomonnaies vaudrait probablement des dizaines de millions de dollars par jour.
    Si vous êtes un ami, ne conseillez pas à vos amis d’utiliser un système de chat sans chiffrement de bout en bout. Ne soyez pas le miel dans le piège.

    • Rappelons encore une fois que tout ce que vous envoyez sur un forum, DM compris, est enregistré en clair et accessible aux administrateurs.
      C’est normal si vous n’utilisez pas l’un des rares services qui ont mis en œuvre un vrai modèle zero trust où l’utilisateur gère lui-même ses clés. La raison pour laquelle les messages sont stockés est de permettre aux utilisateurs d’y accéder à nouveau.
      Il existe des services comme Matrix qui gèrent la messagerie de groupe chiffrée de bout en bout de façon relativement conviviale, mais ils relèvent plutôt de l’exception. Il n’est pas juste de dépeindre Discord comme particulièrement malveillant simplement parce qu’il fonctionne comme 95 % des plateformes de communication électronique.
    • « Le simple fait d’avoir un compte normalise cela », mais c’est déjà normalisé depuis longtemps, et Discord a gagné.
      Je ne dis pas que c’est une bonne chose, mais dans certaines communautés, il n’y a pas vraiment d’autre choix que de ne pas participer.
      C’est encore pire que l’ancien « tout le monde utilise WhatsApp ». À l’époque, on avait le numéro de la personne, donc il était facile de la contacter autrement ; l’attrait de Discord, lui, ne tient pas aux conversations privées, mais aux communautés avec des espaces semi-publics. Ici, « public » ne veut pas dire ouvert à tout le monde, mais plutôt lu par une centaine de personnes.
    • Heureusement, Discord propose une suppression des messages sans trace.
      Quand on supprime un message, il n’est plus stocké dans la base de données.
  • Récemment, OpenAI a soudainement désactivé son Discord pour bêta-testeurs, ce qui nous empêche désormais de voir avec qui nous discutions et de quoi.
    Je me demandais s’il existait un moyen d’exporter les chats pour éviter que l’administrateur du serveur ne puisse couper la communauté les uns des autres sans même laisser la possibilité de parcourir l’historique.
    Il existe pas mal d’extensions Chrome pour exporter les chats Discord, mais la plupart semblent verrouiller certaines fonctions derrière une offre payante.
    Il s’est avéré qu’il était très facile de copier la source de l’extension depuis le dossier Chrome, de modifier dans le JavaScript un test booléen du genre is_pro, puis de la recharger comme extension non empaquetée.

    • DiscordChatExporter : https://github.com/Tyrrrz/DiscordChatExporter
      C’est un programme autonome qui utilise l’API de façon non standard, mais je ne crois pas avoir encore vu quelqu’un se faire bannir pour l’avoir utilisé.
  • L’article prévient correctement que ce genre d’astuce peut entraîner un bannissement, mais Discord a-t-il déjà banni des utilisateurs pour ce genre de choses ?

    • Discord n’a aucun scrupule à bannir des gens pour n’importe quelle raison.
      Ils interdisent aussi l’usage de clients alternatifs. Si votre compte est important, mieux vaut ne pas bricoler avec Discord.
    • Le README de Vencord, l’un des mods les plus populaires, dit ceci :
      « Modifier le client est contraire aux conditions d’utilisation de Discord. »
      Cela dit, Discord semble assez indifférent à ce sujet, et il n’existe aucun cas connu de bannissement simplement pour avoir utilisé des mods de client. Donc, tant que vous n’utilisez pas de plugins qui implémentent des comportements abusifs, ça devrait globalement aller. Pas besoin de s’inquiéter : les plugins intégrés sont tous censés être sûrs.
  • Je peux comprendre que certains thèmes s’activent ainsi, mais il est assez difficile de comprendre pourquoi ils ont laissé la qualité du streaming être décidée par une vérification côté client plutôt que côté serveur.

    • D’autant plus qu’il suffit de vérifier le débit binaire en entrée/sortie.
      Il n’est même pas nécessaire d’accéder à la vidéo elle-même ; même si elle est entièrement chiffrée, la quantité de données transmises indique à quelle qualité le flux est diffusé.
  • Le grand principe de l’ingénierie frontend se vérifie une fois de plus :
    « Ne jamais, jamais faire confiance au client. »

  • Depuis que j’ai vu que cela pouvait être géré uniquement côté client, j’utilise régulièrement les outils de développement pour activer le bouton de streaming 1080p60, et ça fonctionne vraiment.
    Je ne sais pas depuis combien d’années, mais personne chez Discord ne semble s’en soucier.

  • J’avais essayé de suivre cette voie auparavant, mais j’avais fini par abandonner, surtout parce que je n’avais pas trouvé de moyen de patcher le client de façon cohérente après les mises à jour.
    Mais en voyant cette méthode, ça me redonne envie de « l’ouvrir et de bidouiller dedans ».
    Existe-t-il un moyen simple de parcourir les API disponibles de cette manière ? J’avais essayé de tout journaliser, mais c’était un bazar énorme avec les maps, l’internationalisation, etc. Je me demande si quelqu’un s’est donné la peine de produire une sorte de documentation de rétro-ingénierie.