Stéganographie et format JPEG

a marqué ce sujet comme résolu.

Bonjour à tous,

Il est apparemment impossible de cacher des données au sein d’une image JPEG, et je voudrais savoir pourquoi.

Rappels sur la compression JPEG

Les images JPEG ont subi plusieurs étapes afin d’être compressées :

  1. Calcul de tous les coefficients possibles et sélection des coefficients adaptés ;

  2. Décomposition de l’image en 3 plans : Y, U et V et chaque plan correspond à la fréquence du point : f(x, y) ;

  3. L’image est ensuite décomposée en blocs de 64 pixels (8x8) ;

  4. Chaque bloc subit une Transformation en Fourier Rapide bidirectionnelle (FTT, Fast Fourier Transform) ;

  5. A ce stade, chaque bloc correspond à 64 pairs de fréquence et d’orientation ;

  6. Selon la qualité désirée par l’utilisateur, la quantification vectorielle OU BIEN l’élimination des coefficients de contribution minime, généralement les hautes fréquences, peuvent être utilisées ;

  7. Le codage se termine par la compression puis la sauvegarde de l’image en JPEG.

Les coefficients dont je parle au point n°5 sont ceux retenus à l’étape n°0.

Rappels sur la stéganographie (cacher des données dans une image)

  1. On rend impair la quantité de rouge d’une image "A".

  2. On prend l’image "B" que l’on souhaite cacher dans "A". "B" contient des pixels soit noirs soit blancs (noirs => présence d’une donnée, blanc => absence de donnée). "B" fait la même taille que "A".

  3. Là où on un pixel est noir dans "B", on ajoute 1 dans le pixel de même coordonnées (dans "A"). Sinon, on ne fait rien.

  4. Puis on enregistre l’image : le format ne doit pas être JPEG.

Note : on peut faire de même pour le vert et le bleu (donc on peut cacher 3 images dans une même image, une pour le plan rouge, une autre pour le plan bleu et une autre pour le plan vert).

Question principale

Justement : en quoi le fait d’enregistrer une image au format JPEG est-il impossible avec mon algorithme de stéganographie ?

Déjà : est-ce à cause de la compression puis sauvegarde de l’image vers JPEG ? Ou bien est-ce lors de la phase de décompression puis affichage du JPEG ?

Puis : en détails, où est le problème ?

Question secondaire

Juste au cas où : est-ce que je me suis trompé dans mes explications concernant la compression et sauvegarde vers JPEG ? Ou trouvez-vous que je manque de précision ? N’hésitez pas à me ré-expliquer ça si vous en avez le temps :-°

Bonnes fêtes de fin d’année à vous :magicien:,

Ton algorithme de stéganographie est faux pour commencer. Pour la stéganographie d’une image dans une autre, on utilise les bits de poids faibles d’un pixel (ici le dernier) pour encoder les bits de poids forts (bon, ici 0 ou 1) de l’image à cacher.

Si tu incrémente si c’est noir, et laisse ainsi si c’est blanc, comment tu vas faire pour extraire l’image cachée ? Bah tu ne peux pas, tu as perdue l’information de savoir quel pixel est noir ou blanc…

Sinon, concernant le JPEG, le soucis est qu’il va modifier l’image source pour compresser et en particulier les bits de poids faible de tes pixels. Tu vas donc perdre de l’information, et comme ce sont les bits de poids fort de ton image, elle sera fortement détériorée.

C’est pourquoi le JPEG n’est jamais utilisé pour cela. Il faut du sans perte.

+0 -0

Pour la question secondaire, certains points de ton explication sont rapides/flous. J’ai un article en cours d’écriture sur le sujet, la bêta est disponible.

Anto59290

Merci, je vais voir ça !

Ton algorithme de stéganographie est faux pour commencer. Pour la stéganographie d’une image dans une autre, on utilise les bits de poids faibles d’un pixel (ici le dernier) pour encoder les bits de poids forts (bon, ici 0 ou 1) de l’image à cacher.

Si tu incrémente si c’est noir, et laisse ainsi si c’est blanc, comment tu vas faire pour extraire l’image cachée ? Bah tu ne peux pas, tu as perdue l’information de savoir quel pixel est noir ou blanc…

Sinon, concernant le JPEG, le soucis est qu’il va modifier l’image source pour compresser et en particulier les bits de poids faible de tes pixels. Tu vas donc perdre de l’information, et comme ce sont les bits de poids fort de ton image, elle sera fortement détériorée.

C’est pourquoi le JPEG n’est jamais utilisé pour cela. Il faut du sans perte.

Renault

Je ne comprends pas en quoi mon algo est faux. Je mets le rouge de chaque pixel de l’image-source en impair, puis si dans l’image à cacher il y a un pixel noir de mêmes coordonnées, je change la couleur de l’image-source en pair.

Du coup j’enregistre.

Pour récupérer l’image cachée, je parcours chaque pixel de l’image : là où il y a du rouge pair, c’est qu’il y a une donnée c’est tout. Là où il y a de l’impair, c’est rien.

Je l’ai déjà fait et ça marche très bien =/

La quantification a lieu après l’étape qui transforme les luminosités en fréquences d’après le tuto d’Anto, du coup est-ce que ce n’est pas un peu ces deux points qui posent problème ?

Si c’est uniquement la quantification, peux-tu développer un peu plus et ainsi expliquer plus en détails ce qui se passe avec mes bits s’il te plaît ? =/

Il y a déjà les réponses à tes questions dans le tuto d’Anto59290. Il explique à propos de la FFT :

cette opération est non destructrice, mais le calcul avec des virgules flottantes peut provoquer des erreurs d’approximation.

Autrement dit, la FFT par elle-même va déjà effectivement empêcher l’utilisation du JPEG pour passer un message, non pas à cause d’un problème intrinsèque mais parce que les calculs sur les flottants ne sont pas parfaits.

Anto59290 explique ensuite à propos de la quantification (qui consiste en gros à virer les grandes fréquences) :

Les divisions des coefficients va produire des nombres réels, que nous allons arrondir afin de ne travailler qu’avec des entiers. Cette étape est destructive est fait perdre des informations de manière non réversible.

Ici il y a perte d’information par arrondi, c’est en pratique beaucoup plus violent que les petites erreurs de calcul flottant lors de la FFT. On enlève carrément volontairement de l’information de l’image. Et évidemment, l’information que tu as ajouté par stéganographie est soumise elle aussi à ce filtre et il y a de très fortes chances pour qu’une partie de cette information soit bêtement éliminée par l’arrondi. Le cas extrême serait d’avoir une image unie et que tu ne changes qu’un seul pixel en plein milieu. Lors de la FFT, ton pixel en plein milieu va être vu comme du signal à très haute fréquence (mais ne sera pas perdu à ce stade). Lors de la phase de quantification, ce signal très haute fréquence va être arrondi à 0 et tu vas te retrouver en sortie avec ton image unie de départ, sans trace de l’information que tu as ajoutée.

En effet j’ai zappé cette étape. Notons qu’elle est inutile, tu peux directement mettre le résultat 0 ou 1 dans le dernier bit de ta composante rouge…

Renault

Et ça éviterait le problème de dépassement qui peut actuellement avoir lieu. Si ton pixel a une composante rouge de 255, et que tu veux stocker y le bit 1, tu dépasses.

Attention à ne pas réduire la stéganographie à cette technique de Stéganographie !

Il est biensûr possible de faire de la stéganographie dans une Image jpg !

Mais pas avec cette technique effectivement. Car justement le jpg modifie les bits de poids faible lors de sa compression. Ce n’est pas un format sans perte.

Par-contre, oui tu peux faire de la stéganographie avec du jpg. Car il existe beaucoup de techniques.

+1 -0

Autrement dit, la FFT par elle-même va déjà effectivement empêcher l’utilisation du JPEG pour passer un message, non pas à cause d’un problème intrinsèque mais parce que les calculs sur les flottants ne sont pas parfaits.

Si je rends pair un rouge impair, ça va donner un flottant qui sera utilisé par la FTT et c’est ce qui fera disparaître cette info ?

Ici il y a perte d’information par arrondi, c’est en pratique beaucoup plus violent que les petites erreurs de calcul flottant lors de la FFT. On enlève carrément volontairement de l’information de l’image.

Heum pas sûr d’avoir bien pigé argh .. =/

Le cas extrême serait d’avoir une image unie et que tu ne changes qu’un seul pixel en plein milieu. Lors de la FFT, ton pixel en plein milieu va être vu comme du signal à très haute fréquence (mais ne sera pas perdu à ce stade). Lors de la phase de quantification, ce signal très haute fréquence va être arrondi à 0 et tu vas te retrouver en sortie avec ton image unie de départ, sans trace de l’information que tu as ajoutée.

Ah là je comprends mieux déjà :p

Mais pourquoi ce pixel serait-il considéré comme un filtre à très haute fréquence ? Dans le cadre de mon algo de stéganographie je veux dire.

Autrement dit, la FFT par elle-même va déjà effectivement empêcher l’utilisation du JPEG pour passer un message, non pas à cause d’un problème intrinsèque mais parce que les calculs sur les flottants ne sont pas parfaits.

Si je rends pair un rouge impair, ça va donner un flottant qui sera utilisé par la FTT et c’est ce qui fera disparaître cette info ?

FFT, pas FTT… Ensuite, ce sont les calculs effectués pour faire la FFT qui font intervenir des flottants, et il est possible (mais ce n’est pas obligatoire) que de l’information soit perdue lors de ces opérations sur les flottants.

Ici il y a perte d’information par arrondi, c’est en pratique beaucoup plus violent que les petites erreurs de calcul flottant lors de la FFT. On enlève carrément volontairement de l’information de l’image.

Heum pas sûr d’avoir bien pigé argh .. =/

Il n’y a rien à comprendre, on enlève des fréquences donc on perd de l’info.

Le cas extrême serait d’avoir une image unie et que tu ne changes qu’un seul pixel en plein milieu. Lors de la FFT, ton pixel en plein milieu va être vu comme du signal à très haute fréquence (mais ne sera pas perdu à ce stade). Lors de la phase de quantification, ce signal très haute fréquence va être arrondi à 0 et tu vas te retrouver en sortie avec ton image unie de départ, sans trace de l’information que tu as ajoutée.

Ah là je comprends mieux déjà :p

Mais pourquoi ce pixel serait-il considéré comme un filtre à très haute fréquence ? Dans le cadre de mon algo de stéganographie je veux dire.

The-Aloha-Protocol

Comme un signal, pas comme un filtre… C’est mathématique, ça n’a rien à voir avec ton algo. Ça vient simplement de la définition de la FFT, un pixel isolé va donner une grande fréquence dans le domaine de Fourier (et c’est pour ça qu’on vire les hautes fréquences pour compresser, parce que ce sont celles qui correspondent à des variations sur une petite échelle d’espace que l’oeil humain a du mal à voir).

+0 -0
Connectez-vous pour pouvoir poster un message.
Connexion

Pas encore membre ?

Créez un compte en une minute pour profiter pleinement de toutes les fonctionnalités de Zeste de Savoir. Ici, tout est gratuit et sans publicité.
Créer un compte