2009-06-27 8 views
0

Est-ce que quelqu'un connaît un PHP RegEx pour autoriser uniquement les chemins relatifs, pas absolus? Par exemple, j'ai une fonction AJAX qui soumet cette valeur à mon script PHP "some-directory/another-directory/some-file.php".Débutant RegEx Question - PHP RegEx pour autoriser uniquement les chemins relatifs (pas les URL)

Mon script PHP inclut alors ce fichier .... include ($ some-php-document);

Je ne veux pas un pirate pour être en mesure d'utiliser ma fonction AJAX pour présenter quelque chose comme: « http://www.malicious-website.com/malicious-script.php »

Dans mon document PHP Je voudrais faire quelque chose comme:

<php> 
$some-php-document = $_POST["some_value_submitted_via_ajax"]; 

//if $some-php-document is a URL (not a relative path to a file), 
    //then $some_php_document = null 

//how can I use a php regex to accomplish the above? 

</php> 

Comment puis-je faire ceci?

Ou, laissez-moi savoir s'il existe des solutions plus sécurisées.

Répondre

2

Je voudrais utiliser la fonction parse_url() plutôt qu'une expression rationnelle, quelque chose comme:

<?php 
$some_php_document = $_POST["some_value_submitted_via_ajax"]; 

$parsed_doc = parse_url($some_php_document); 

//if $some-php-document is a URL (not a relative path to a file), 
    //then $some_php_document = null 
if (isset($parsed_doc['scheme']) || isset($parsed_doc['host'])) { 
    $some_php_document = null; 
} 

?> 

Le chemin du fichier sera parsed_doc de $ [ 'path']. Il devrait être vérifié avant d'être utilisé, donc un attaquant ne peut pas dire, demander/etc/passwd ou un fichier similaire sensible.

+0

Les utilisateurs du programme doivent être en mesure de spécifier un chemin, donc je ne sais pas un bon moyen de vérifier. Ce que j'ai fait à la place était d'utiliser votre exemple et d'inclure l'instruction include dans ob_start() et ob_end clean(). De cette façon, si un pirate inclut un fichier sensible qui fait écho à du contenu, le contenu renvoyé sera détruit. S'il vous plaît laissez-moi savoir si vous avez une meilleure idée. – edt

0

Vous pouvez tester: // dans la chaîne et si elle est présente, rejeter. Si vous voulez une expression régulière négative, essayer quelque chose comme:

^([^:]|:[^/]|:/[^/})*$ 

Si elle correspond, la chaîne est relative (bien que peut-être malformé).

+0

Le protocole n'est pas requis dans une URL. //otherserver.com/script.js est valide. –

+0

Etes-vous sûr? Je viens d'entrer cette adresse dans mon navigateur et il fichier auto-rempli: // – Blindy

3

Ne pas autoriser le téléchargement de noms de fichiers pour spécifier un include. Au lieu de cela faire ceci:

$valid_files = array(
    'file1' => 'file1.inc', 
    'file2' => 'john.inc', 
    'fred' => 'bob.inc', 
); 

$requested_include = trim(strtolower($_POST["some_value_submitted_via_ajax"]))); 
if (!array_key_exists($requested_include, $valid_files)) { 
    $requested_include = "file1"; 
} 
include WEB_ROOT_PATH . 'templates/whatever/' . $valid_files[$requested_include]; 

Valider toutes les entrées, pas besoin d'un RegEx - il est difficile d'obtenir le droit et vous êtes mieux avec une solution de sécurité plus strictes comme ci-dessus.