PROJET AUTOBLOG


Le Kernel Panique (Kpanic)

Archivé

source: Le Kernel Panique (Kpanic)

⇐ retour index

WordPress 4.3 casse la mise à jour via SSH/SFTP

mardi 8 septembre 2015 à 09:58

Si vous avez un WordPress installé dans un hébergement sécurisé, vous utilisez probablement la mise à jour via SSH/SFTP pour effectuer les mises à jour. Seulement depuis WordPress 4.3 ce n’est plus possible à cause d’un bug introduit.

La mise à jour a échoué : La mise à jour ne peut pas être installée parce que nous n’allons pas pouvoir copier certains fichiers. Ce problème est généralement dû à des incohérences dans les permissions de fichiers.

Les développeurs de WordPress ont ajouté dans la version 4.3 une vérification, qui ne se comporte pas comme il faut, apparemment lié au support SSH/SFTP de PHP.

Les développeurs ont déjà réfléchis à une solution, et proposent un work-arround.

Pour appliquer ce work-arround, télécharger le fichier suivant, et patcher le code de votre WordPress avec. Voici un exemple en ligne de commande.

$ cd /home/monsite/www/wp-admin/includes/
$ wget "https://core.trac.wordpress.org/changeset/33688/trunk/src/wp-admin/includes/class-wp-filesystem-ssh2.php?format=diff&new=33688" -O /tmp/WP_ssh.patch
$ patch -p4 < /tmp/WP_ssh.patch

Vous devriez maintenant pouvoir mettre à jour vos plugins/thèmes.
Le problème sera corrigé avec la version 4.3.1.

Un Windows 10 libre

dimanche 6 septembre 2015 à 23:35

Titre troll :-)
En Août chez Evolix, on a une prime d’intéressement. C’est l’occasion d’en profiter pour faire un don à mes logiciels libres préférés que j’utilise tout les jours ! Je vais me baser sur le prix d’une licence Windows 10 qui coûte 120$ (amazon.com) dans son édition familiale.

Total = 136$

 

Déchiffrer les sous-titres KZPlay + capture vidéo

mardi 14 juillet 2015 à 22:30

KZPlay était une ancienne plate-forme de VOD d’animés dont les vidéos possédait des sous-titres « softsubs » non intégrés à la vidéo.
C’est maintenant ADN qui a pris le relais de cette ancienne plate-forme. ADN utilise toujours des « softsubs », mais la technique de chiffrement n’est pas la même. Je me permets donc de diffuser publiquement cette article comme « étude de cas » qui − à priori − ne nuira pas à KZPlay/ADN.

/!\ Attention, technique /!\

Regardons le code source de l’applet flash.

<object id="mediaspaceba" width="100%" height="100%" type="application/x-shockwave-flash" data="http://kzplay.fr/components/com_vodvideo/mediaplayer/player.swf" bgcolor="#000000" name="mediaspaceba" tabindex="0">
<param name="allowfullscreen" value="true">
<param name="allowscriptaccess" value="always">
<param name="seamlesstabbing" value="true">
<param name="wmode" value="opaque">
<param name="flashvars" value="netstreambasepath=http%3A%2F%2Fkzplay.fr%2Fvideo%2Fto_love_darkness&id=mediaspaceba&image=http%3A%2F%2Fimage.kzplay.fr%2Flicense%2Ftoloveru%2Ftv3%2Fweb%2Feps1_729x410.jpg&skin=http%3A%2F%2Fkzplay.fr%2Fcomponents%2Fcom_vodvideo%2Fmediaplayer%2Fblueratio%2Fblueratio.zip&bufferlength=16000&repeat=list&title=La%20suite&autostart=false&plugins=http%3A%2F%2Fkzplay.fr%2Fcomponents%2Fcom_vodvideo%2Fmediaplayer%2Fplugins%2Fova%2Fova-jw.swf%2Chttp%3A%2F%2Fkzplay.fr%2Fcomponents%2Fcom_vodvideo%2Fmediaplayer%2Fplugin...va.canFireAPICalls=false&ova.ads=%5B%5BJSON%5D%5D%7B%22pauseOnClickThrough%22%3Afalse%2C%22enablePause%22%3Afalse%2C%22schedule%22%3A%5B%7B%22position%22%3A%22pre-roll%22%2C%22tag%22%3A%22http%3A%2F%2Fkzplay.fr%2Fpreroll.php%22%2C%22applyToParts%22%3A%5B0%5D%2C%22mulutibu.hidden%22%3Atrue%7D%5D%7D&ova.debug=%5B%5BJSON%5D%5D%7B%22levels%22%3A%22none%22%7D&ova.pluginmode=FLASH&control.pluginmode=FLASH&mulutibu.back=false&mulutibu.cc=false&mulutibu.pluginmode=FLASH&controlbar.position=over&dock.position=true">
</object>

La partie flashvars contient tout un tas de paramètres, décodons-les avec un urldecode.

netstreambasepath=http://kzplay.fr/video/to_love_darkness
&id=mediaspaceba
&image=http://image.kzplay.fr/license/toloveru/tv3/web/eps1_729x410.jpg
&skin=http://kzplay.fr/components/com_vodvideo/mediaplayer/blueratio/blueratio.zip
&bufferlength=16000
&repeat=list
&title=La suite
&autostart=false
&plugins=
    http://kzplay.fr/components/com_vodvideo/mediaplayer/plugins/ova/ova-jw.swf,
    http://kzplay.fr/components/com_vodvideo/mediaplayer/plugins/control/control.swf,
    http://kzplay.fr/components/com_vodvideo/mediaplayer/plugins/mulutibu/mulutibu.swf
&playlist=[[JSON]]
    [{
        "file": "http://dmeizi6er88hs.cloudfront.net/aod/LogoKAZE.mp4",
        "sd.vf": null,
        "sd.vo": "http://dmeizi6er88hs.cloudfront.net/aod/LogoKAZE.mp4",
        "default": "http://dmeizi6er88hs.cloudfront.net/aod/LogoKAZE.mp4",
        "mulutibu.hidden": true,
        "image": "http://image.kzplay.fr/license/toloveru/tv3/web/eps1_729x410.jpg"
    }, {
        "start": 0,
        "mulutibu.hidden": false,
        "image": "http://image.kzplay.fr/license/toloveru/tv3/web/eps1_729x410.jpg",
        "ccid": "2701",
        "streamer": "rtmpe://ec2-46-137-138-250.eu-west-1.compute.amazonaws.com/redirect?bufferlenght=16",
        "provider": "rtmp",
        "rtmp.tunneling": false,
        "sd.vo": "default",
        "file": "a3a2dc8d99300191a0175bf3482cad75.mp4?audioIndex=0",
        "default": "a3a2dc8d99300191a0175bf3482cad75.mp4?audioIndex=0"
    }]
&ova.clearPlaylist=false
&ova.assessControlBarState=false
&ova.canFireAPICalls=false
&ova.ads=[[JSON]]{
    "pauseOnClickThrough":false,
    "enablePause":false,
    "schedule":[{
        "position":"pre-roll",
        "tag":"http://kzplay.fr/preroll.php",
        "applyToParts":[0],
        "mulutibu.hidden":true
    }]
}
&ova.debug=[[JSON]]{"levels":"none"}
&ova.pluginmode=FLASH
&control.pluginmode=FLASH
&mulutibu.back=false
&mulutibu.cc=false
&mulutibu.pluginmode=FLASH
&controlbar.position=over
&dock.position=true

3 plugins JWPlayer sont chargés : ova-jw.swf, control.swf et mulutibu.swf.

ova-jw est à priori un truc permettant d’afficher une publicité avant de lancer une vidéo… passons. control est un module pour interagir avec la barre de contrôle (play/pause, etc.).
Enfin, ce qui nous intéresse mulutibu.swf, en cherchant sur internet, rien, le néant, qu’est-ce donc ?

Gestion des sous-titres (mulutibu.swf)

Et oui ! C’est lui qui va afficher les sous-titres sur la vidéo. Décompressons-le et regardons les chaînes de caractères qu’il contient en dur :

flasm -x mulutibu.swf
strings mulutibu.swf
[... Tronqué ...]
<dc:title>Adobe Flex 4 Application</dc:title>
void!com.longtailvideo.jwplayer.player
IPlayer"com.longtailvideo.jwplayer.plugins
Mulutibu+com.longtailvideo.plugins.mulutibu:Mulutibu
SRT&com.longtailvideo.plugins.mulutibu:SRT+com.longtailvideo.plugins.mulutibu:Renderer  _captions       _playResX       _playResY
decryptSubtitle
base64charsAABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=
encode
decode
No captions entries found in file. Probably not a valid SRT or DFXP file?
Japonais        Fran
backcolour
textFormat
Dialogue!^Dialogue\:\s?((?:(?:[^,]*)\,?)+)

Pas de doute possible, c’est bien ce qui permet l’affichage des sous-titres, qui seraient d’ailleurs protégés via un système d’encodage (en base64 ?!).

Où sont les sous-titres ?
Analysons les requêtes HTTP lors de la lecture de la vidéo. Hop on récupère (http://kzplay.fr/picture_2701.png) qui de toute évidence n’est pas un fichier png… Ce sont nos sous-titres ! On trouve ceci dans le swf de mulutibu :

strings mulutibu.swf| grep pict
ccid    /picture_

Les sous-titres sont donc stockés ici : kzplay.fr/picture_ccid.png. ccid correspondant à l’ID de la vidéo.

Ce fichier est illisible, il est donc encodé via un algorithme particulier, voyons comment on pourrait le décoder. Pour cela, dé-compilons cette application flex avec le flex-sdk d’Adobe (OpenSource). On obtiens du bytecode AS, pas très lisible.

swfdump -acb mulutibu.swf > mulutibu.acb

On y trouve plusieurs fonctions intéressantes, qui indique clairement que c’est bien le module qui va, décrypter, parser, et afficher les sous-titres :

function com.longtailvideo.plugins.mulutibu:Mulutibu:::decryptSubtitle(:String, :String)::String
function com.longtailvideo.plugins.mulutibu:SRT:::parseCaptions(:Array)::Array
function com.longtailvideo.plugins.mulutibu:ASS:::parseCaptions(:Array)::Array
function com.longtailvideo.plugins.mulutibu:Renderer::private:_renderCaption(:Array)::void

On va dé-compiler ce petit swf avec une application gratuit de HP (oui oui HP) : SWFscan (Outil Windows :().
On trouvera facilement la fameuse fonction decryptSubtitle, elle est assez simple. Bref, plus qu’à la convertir bêtement/salement dans le langage de son choix (ici PHP) et on obtient un décodeur.

<?php
// Decompiled flash/flex/AS code.
// public static function decryptSubtitle(arg0:String, arg1:String = "5463201897") : String
// {
//     var loc4:* = null;
//     var loc5:* = 0;
//     var loc6:* = 0;
//     var loc7:* = 0;
//     var loc0:* = new ByteArray();
//     var loc1:* = "";
//     var loc2:* = 0;
//     while(loc2 < arg0.length)
//     {
//         loc4 = arg0.substr(loc2, 1);
//         loc5 = parseInt(arg1.substr(loc2 % arg1.length - 1, 1));
//         loc6 = loc4.charCodeAt(0);
//         loc7 = loc4.charCodeAt(0) - loc5;
//         loc4 = String.fromCharCode(loc7);
//         loc1 = loc1 + loc4;
//         loc2++;
//     }
//     var loc3:* = replace(new RegExp(""), "");
//     loc0.writeMultiByte(loc3, "iso-8859-1");
//     return loc0.toString();
//     
// }
function decryptSubtitle($encryptedSub, $key = "5463201897") {

    $loc4 = null;
    $loc5 = 0;
    $loc6 = 0;
    $loc7 = 0;
    $loc0 = array();
    $loc1 = "";
    $loc2 = 0;
    while ($loc2 < strlen($encryptedSub)) {
        $loc4 = substr($encryptedSub, $loc2, 1); // Progress byte by byte.        
        /* Convert the value to integer ($loc2 % 10)-1. */
        $loc5 = intval(substr($key, (($loc2 % (strlen($key)) - 1)), 1));
        $loc6 = ord($loc4); //Get the ASCII code of the char.
        $loc7 = ord($loc4) - $loc5; // ASCII char. - calculated value.
        $loc4 = chr($loc7); // Get the final character from  ASCII code.
        $loc1 = $loc1 . $loc4; // Store the final decrypted char.
        $loc2++; // Go to next byte.
    }
    echo base64_decode($loc1);
}

$filename = $argv[1];
$handle = fopen($filename, "r");
$contents = fread($handle, filesize($filename));
decryptSubtitle($contents);
?>
php decryptSubtitle.php picture_2701.png > 2701.ass

La technique de chiffrement est relativement faible. Elle consiste à encoder en base64 le fichier de sous-titres, puis changer chaque caractère avec un calcul basé sur un des chiffre de la clé 5463201897 selon la position -1.
Par exemple pour le premier caractère W (87 en ASCII décimale), on calcule ainsi :
La position de ce premier caractère dans la chaîne base64 est 0.
(0 modulo 10) -1 = -1.
On additionne le caractère (87) avec la position -1 de la clé (7).
Soit 87 + 7 = 94, ainsi, W (87), devient ^ (94).

Autre exemple avec le caractère j (106), en position 3.
(3 modulo 10) -1 = 2.
On additionne le caractère (106) avec la position 2 de la clé (6).
Soit 106 + 6 = 112, ainsi, j (106), devient p (112).

C’est donc, un dérivé du chiffre de Vigenère.

Capture de la vidéo (RTMP FMS)

Impossible de capturer la vidéo avec rtmpdump, il faut que je cherche encore pourquoi ce n’est pas possible, dans tout les cas il y a une histoire de loadbalancer. Pour info, voici la liste de tout les serveurs FMS (Wowza Media Server 2) de Kazé.

On va donc utiliser rtmpsuck qui permet de faire un proxy RTMP et de capturer tout ce qui transite.

# iptables -t nat -A OUTPUT -p tcp --dport 1935 -m owner --uid-owner proxy -j ACCEPT
# iptables -t nat -A OUTPUT -p tcp --dport 1935 -j REDIRECT

$ rtmpsuck

Lire la vidéo avec les sous-titres avec mplayer :) !

mplayer mp4_944fb8867af5ff97fab8afabbdd739dd.mp4 -ass -sub 2701.ass

Bonne année 2015

jeudi 1 janvier 2015 à 00:00

Bonne année !
Happy new year!
明けましておめでとう❗

Pour la première fois, petite rétrospective du blog via des statistiques, parce que les statistiques c’est toujours fun !

~17500 visites, contre ~18500 visites en 2013 ;

Top 10 des mots-clés utilisés dans les moteurs de recherches pour tomber sur le blog :

Top 5 des articles les plus visités :

Miam, des camemberts !

 

searchengines
Moteur de recherches utilisés pour tomber sur le blog.
references
Visites via d’autres sites.
devices
Type de “device” utilisé.
chartbrowers
Navigateur des visiteurs.
OS
Système d’exploitation utilisé.
resolution
Résolution des visiteurs. Quelle résolution pour 2015 ? Aha !
langages
Langages des navigateurs.
country
Pays des visiteurs.

Merry Christmas!

jeudi 25 décembre 2014 à 00:00

Joyeux Noël !
Merry Christmas!
メリクリマス!