Codec d'obfuscation de lien html (php5)

Soyez le premier à donner votre avis sur cette source.

Snippet vu 6 955 fois - Téléchargée 14 fois

Contenu du snippet

Il est souvent dangereux d'envoyer en clair les paramètres d'appels d'une pages html car celà donne des indications à tout le monde sur comment ils sont formés et comment on peut les exploiter pour trouver des failles dans le script.

Les mettre en base64 n'empêche toujours pas d'en connaitre la nature, mais ça complique un peut les choses, et un hacker ou un pirate, c'est un flemmard : s'il n'y a pas grand chose à piquer, il préfèra aller ailleur où c'est moins sécurisé et/ou là où il y a plus a prendre ;)

(parceque se taper une page de lien à décoder puis à mettre en action et à recoder avant de les injecter dans le browser, ça demande du temps...)

Un niveau supérieur de sécurité est prévu : mélange des paramètres en base64 avec une chaine aléatoire et stockée dans la base de données en correspondance avec le numéro de session
(ex: table session(id_session:char(255),not null;chaine_cryptage:char(255)))

J'y reviendrais plus tard quand je serais devenu plus parano

Source / Exemple :


<?php

/*
///////////////////////////////////
// Copyright LE DREFF Nicolas 2009
// Libre d'utilisation à condition de conserver cette mention
// Merci
// http://www.phpcs.com/codes/CODEC-OBFUSCATION-LIEN-HTML_49615.aspx
/////////////////////////////////
// Classe 'codec' permettant de gérer des liens au format base64
// Exemple d'utilisation:
////////////////////////////////
// ex 1:
// custumization des paramètres; Vous pouvez y mettre ce que vous voulez
///////////////////////////////
<?php
        $anchor_html = new anchor_html();

        $anchor_html->anchor_web_page = 'upload_document.php';

        $anchor_html->anchor_parameters[] = array('anchor_parameter_name'=>'doc_type','anchor_parameter_value'=>DOC_IMAGE);
        $anchor_html->anchor_parameters[] = array('anchor_parameter_name'=>'to_do','anchor_parameter_value'=>'scale');
        $anchor_html->anchor_parameters[] = array('anchor_parameter_name'=>'img_landscape_max_width','anchor_parameter_value'=>800);
        $anchor_html->anchor_parameters[] = array('anchor_parameter_name'=>'img_portrait_max_height','anchor_parameter_value'=>800);
        $anchor_html->anchor_parameters[] = array('anchor_parameter_name'=>'thumbnails_div','anchor_parameter_value'=>'');
        $anchor_html->anchor_parameters[] = array('anchor_parameter_name'=>'id_image','anchor_parameter_value'=>'image_big');
        $anchor_html->anchor_parameters[] = array('anchor_parameter_name'=>'accepted_mimes','anchor_parameter_value'=>'jpg::gif::png');

        $anchor_64_base = $anchor_html->get_anchor_html();
        //echo $anchor_html->anchor_parameters_64_base;
        //echo base64_decode($anchor_html->anchor_parameters_64_base);
        //exit;
        $anchor_html->reset_anchor();
?>
  <iframe id="image_upload" width="600px" height="50px" src="<?php echo $anchor_64_base;?>" frameborder="0"></iframe>
//////////////////////////////////////
// ex 2:
// le lien provient d'une base de données et est donc 'figé'. !!!!!!DOIT DEJA ETRE ASSAINI AVEC rawurlencode()!!!!!!!
/////////////////////////////////////
        $menus_html_anchor_array = new anchor_html();
        $menus_html_anchor_array = explode('?',$this->menus_list[$this->index_menus_list]['menus_lien']);
        $anchor_html->anchor_fil_arianne = $_SERVER['REQUEST_URI'];
        $anchor_html->anchor_web_page = $menus_html_anchor_array[0];
        $anchor_html->anchor_parameters_html = $menus_html_anchor_array[1];
        $anchor_64_base = $anchor_html->get_menus_anchor_html();

        $this->user_menus_content .= '<p class="' . $this->menu_deep_array[($this->menus_deep*2)-1] . '" basic_class="' . $this->menu_deep_array[($this->menus_deep*2)-1] . '" href="' . $anchor_64_base . '" target="iframe_content" type="' . MENUS_DATA_TYPE_ANCHOR_LABEL . '" style="cursor:pointer" onmouseover="this.setAttribute(\'class\',\'' . $this->menu_deep_array[($this->menus_deep*2)-1] . '_over\')" onmouseout="this.setAttribute(\'class\',\'' . $this->menu_deep_array[($this->menus_deep*2)-1] . '\')" id="' . $id_link . '" >' . $label_to_display_root . $this->menus_list[$this->index_menus_list]['menus_label'] . '</p>' . "\n";

//////////////////////////////////////
// dans la page appellée il faut ajouter ceci pour avoir la liste des paramètres sous forme de variables globales (unserialized) du même nom
/////////////////////////////////////

<?php

        if(test_param($_GET['param'],TEST_ALPHA)){
                $anchor_html = new anchor_html();
                $anchor_html->anchor_parameters_64_base = $_GET['param'];
                $anchor_html->get_anchor_parameters();
                foreach($anchor_html->anchor_parameters as $anchor_parameters_index=>$anchor_parameters_value){
                        $name = $anchor_parameters_value['anchor_parameter_name'];
                        $value = $anchor_parameters_value['anchor_parameter_value'];
                        $$name = $value;
                }
        }
?>

  • /
class anchor_html { public $anchor_web_page; // la page vers où je veux faire pointer mon lien public $anchor_parameters; // un tableau d'élements 'ancre' => array(array('anchor_parameter_name'=>'doc_type','anchor_parameter_value'=>DOC_IMAGE),array(...)); public $anchor_parameters_html; // la chaine contenant les paramètres d'appels assainis avec rawurlencode et séparés par des '&' public $anchor_parameters_64_base; // la chaine contenant les paramètres d'appels au format base64 public $anchor_html; // l'ancre complète avec la page d'appel et les paramètres en base64 public $anchor_fil_arianne; // possibilité d'inserer une lien de retour en base64 function __construct() // no comments { $this->anchor_web_page = ''; $this->anchor_parameters = NULL; $this->anchor_parameters_html = ''; $this->anchor_html = ''; $this->anchor_fil_arianne = ''; $this->anchor_parameters_64_base = ''; } // cette fonction permet de nettoyer l'objet pour une deuxième utilisation function reset_anchor() { $this->__construct(); } // on assemble les morceaux pour avoir une url propre function build_anchor_parameters_html() { $this->anchor_parameters_html = ''; // juste pour le cas où... $head_char = ''; // le premier paramètre d'appel ne sera pas précédé du '&' if(!empty($this->anchor_parameters)) // des paramètres d'appels? { $nb_paramters = count($this->anchor_parameters); // oui? combien? for($boucle_parameters = 0;$boucle_parameters < $nb_paramters;$boucle_parameters++) // on boucle { $this->anchor_parameters_html .= $head_char . $this->anchor_parameters[$boucle_parameters]['anchor_parameter_name'] . '=' . rawurlencode($this->anchor_parameters[$boucle_parameters]['anchor_parameter_value']); //construction du paramètre assaini $head_char = '&'; // si paramètre suivant il y a, le '&' le précèdera... } } if(!empty($this->anchor_fil_arianne)) //url de retour? { $this->anchor_parameters_html .= $head_char . 'fil_arianne=' . base64_encode($this->anchor_fil_arianne); // on rajoute le tout au lien en cours } //echo '-à-' . $this->anchor_parameters_html . '-à-'; //exit(); return($this->anchor_parameters_html); // byebye } // demande d'assemblage de l'ancre finale function build_anchor_html() { $this->anchor_html = $this->anchor_web_page . '?param='; // début du lien $this->anchor_html .= $this->encode_anchor_parameters_64_base(); // ajout des paramètres en base64 return($this->anchor_html); } // demande d'assemblage de l'ancre finale pour les menus stocké en BDD qui ont donc une liste de paramètres déja assemblé function build_menus_anchor_html() { $this->anchor_html = $this->anchor_web_page . '?param='; // début du lien $this->anchor_html .= $this->encode_menus_anchor_parameters_64_base(); // ajout des paramètres en base64 return($this->anchor_html); } // demande d'encodage des paramètres function encode_anchor_parameters_64_base() { $this->anchor_parameters_64_base = base64_encode($this->build_anchor_parameters_html()); // assemblage et conversion des paramètres return($this->anchor_parameters_64_base); } // demande d'encodage des paramètres déjà assemblé function encode_menus_anchor_parameters_64_base() { $this->anchor_parameters_64_base = base64_encode($this->anchor_parameters_html); // conversion des paramètres return($this->anchor_parameters_64_base); } // demande de décodage des paramètres base64 function decode_anchor_64_base() { $this->anchor_parameters_html = base64_decode($this->anchor_parameters_64_base); // decodage de l'ancre return($this->anchor_parameters_html); } // demande de restitution des paramètres base64 en tableau function get_anchor_parameters() { $anchor_html_array = explode('&',$this->decode_anchor_64_base()); // on découpe les paramètres $this->anchor_parameters = NULL; // on vide le tableau pour éviter les surprises if(!empty($anchor_html_array)) // des paramètres? { $nb_paramters = count($anchor_html_array); // oui? combien? for($boucle_parameters = 0;$boucle_parameters < $nb_paramters;$boucle_parameters++) // on boucle { $anchor_parameter = explode('=',$anchor_html_array[$boucle_parameters]); // séparation des paramètres et de leur valeur $this->anchor_parameters[] = array('anchor_parameter_name'=>$anchor_parameter[0],'anchor_parameter_value'=>rawurldecode($anchor_parameter[1])); // remplissage du tableau } } return($this->anchor_parameters); } function get_anchor_html() { return($this->build_anchor_html()); // restitution de la variable $anchor_html } function get_menus_anchor_html() { return($this->build_menus_anchor_html()); // restitution de la variable $menus_anchor_html } } ?>

Conclusion :


Il est clair que c'est du basic mais ça marche plutôt pas mal.
Outre de ralentir le processus de hackage, ça présente l'avantage de permettre de former des url complexes avec autant de paramètres que l'on veux avec sans se prendre la tête à mettre du rawurlencode() partout.

Reste à faire:
-possibilité de passer des tableaux ou des objets (si, si, c'est possible comme ça)
-possibilité de choisir le mode soit obfuscation, soit cryptage, soit en clair

A voir également

Ajouter un commentaire

Commentaires

Messages postés
494
Date d'inscription
dimanche 5 octobre 2003
Statut
Membre
Dernière intervention
1 septembre 2011

correction apportée pour le terme PHP5.

Je ne savais pas que l'on devait utiliser les fonctions publiques pour nettoyer les variables et ainsi proteger les fonction descendante... c'est bon à savoir...

Je cherche de bon ouvrages, mais ils sont denrée rare car beaucoup se targuent d'être complets mais après lecture, c'est beaucoup de vent... mais je suis preneur...

Merci
Messages postés
4580
Date d'inscription
samedi 19 janvier 2002
Statut
Modérateur
Dernière intervention
9 janvier 2013
27
"en quoi le fait d'avoir toutes mes fonctions publiques soit gênant pour l'encapsulation ?"
Dans l'absolu, ce n'est pas un problème. Dans le cas présent, si la classe ne peut pas contrôler les valeurs qu'on lui injecte par le biais des propriétés publiques, alors il faura blinder chaque méthode.
D'autre part, on ne peut pas comparer la programmation en assembleur et la POO. Si la POO a été inventée c'est, entre autres, pour faciliter la réutilisation (ce qui n'est pas le cas de l'assembleur) et, le plus important à mes yeux, pour que le développeur n'expose pas à l'extérieur de la classe les données sensibles. C'est bien pour cela qu'on été inventées les portées public, protected et private. Pour que l'accès aux propriétés de ta classe soit maîtrisé, l'utilisation d'accesseurs (les fameux getters et setters) est chaudement recommandé. Si tu as un peu de temps, je te recommande la lecture d'ouvrages traitant de ce sujet.
Et je suis d'accord avec toi pour reconnaitre que la notion en PHP4 était un peu légère.
Dernier point, tu devrais préciser que ton code nécessite PHP5 car le constructeur __construct ne sera pas reconnu dans le cas de PHP4.
Cordialement
Messages postés
494
Date d'inscription
dimanche 5 octobre 2003
Statut
Membre
Dernière intervention
1 septembre 2011

Bonjour.
C'est clair, il faudrait normaliser tout ça.

En fait, j'utilise les variables internes de l'objet comme on utilise le stack en assembleur et les fonctions sont les interruptions. De ce fait, mes variables sont plus des paramètres d'appels qu'autre chose. Donc dans ce sens, il faut qu'elles soient publiques.

Il y a ainsi une zone commune à tout l'objet (CR,CX,DS,etc. en assembleur) dans laquelle on vient positionner certaines valeurs avant de déclencher la fonction (interruption). Cela présente l'avantage de ne pas avoir a définir en dur les paramètres d'appels des procédures. Comme ça, si je modifie le code de la procédure lors des mises à jour, je n'ai pas à modifier les appels dans les aplis qui dépendent de cet objet. L'important est de bien initialiser les variables lors de la création de l'objet. Comme ça, si une variable n'est pas positionnée avant l'appel (version antérieur d'appel) la fonction fait son travail sans sourcilier. L'intérêt est plus flagrant dans le cas ou l'on veux supprimer un paramètre d'appel. Il faudrait alors reprendre tous les appels pour les modifiers en correspondance.

Maintenant, il est vrais que certaines fonctions pourraient être privées, mais la POO en PHP5 est un nouveau domaine d'activités pour moi (mes clients étaient en PHP4) et je ne gère pas encore assez bien toute la terminologie qui lui est associée.

Question:
en quoi le fait d'avoir toutes mes fonctions publiques soit gênant pour l'encapsulation?

Merci
Messages postés
4580
Date d'inscription
samedi 19 janvier 2002
Statut
Modérateur
Dernière intervention
9 janvier 2013
27
Bonjour à tous.
Développer une classe où toutes les méthodes et les propriétés sont publiques revient à coder des fonctions classiques et à utiliser des variables globales. Où se situe l'intérêt alors si on peut, de l'extérieur de la classe, injecter n'importe quoi comme valeur dans les propriétés ?
L'intérêt de la POO n'est-il pas, entre autres, de permettre l'encapsulation ?
Sinon, l'idée de départ est bonne.
Messages postés
494
Date d'inscription
dimanche 5 octobre 2003
Statut
Membre
Dernière intervention
1 septembre 2011

Que ma source avait été désactivée pour une raison inconnue.
J'ai sauté l'étape 'terminer' pour arriver directement à ma sources publiée mais désactivée...
c'est pour ça que j'ai contacté malalam cette nuit.
Je pensait qu'il t'avait transmit le problème.
Afficher les 8 commentaires

Vous n'êtes pas encore membre ?

inscrivez-vous, c'est gratuit et ça prend moins d'une minute !

Les membres obtiennent plus de réponses que les utilisateurs anonymes.

Le fait d'être membre vous permet d'avoir un suivi détaillé de vos demandes et codes sources.

Le fait d'être membre vous permet d'avoir des options supplémentaires.