-1

Hey guy's i'm making a website which involves submiting an ad for a gameserver. I'm wondering if it is possible to strip PHP related tags from the content of the textbox? As if I leave it how it is now, It may become a security risk later on. Currently the only thing I am doing to the content is nl2br(). What is the best way to do this?

Thanks.

artlung
  • 33,305
  • 16
  • 69
  • 121
Duncan Palmer
  • 2,865
  • 11
  • 63
  • 91
  • Do you mean PHP *tags* or PHP *function call strings*? – BenM Nov 03 '11 at 18:45
  • possible duplicate of [PHP: the ultimate clean/secure function](http://stackoverflow.com/questions/4223980/php-the-ultimate-clean-secure-function) – Alex Turpin Nov 03 '11 at 18:45
  • You can't execute PHP from the user by accident unless you're doing some very weird stuff with `eval`. You should worry about HTML, and for that, use `htmlspecialchars`. – Alex Turpin Nov 03 '11 at 18:48
  • I mean PHP tags. @Billy Moon It's not a code problem I just need some direction as to how to do it. But since you want it I'll add my sumbmission code. and it's not a duplicate. – Duncan Palmer Nov 03 '11 at 18:50
  • @Xeon06 But wouldn't I have to worry about people posting – Duncan Palmer Nov 03 '11 at 18:51
  • @DuncanPalmer No, you don't. You cannot execute PHP code by displaying it if it is stored in a string. You can execute HTML though. Example:http://codepad.viper-7.com/dOPavX – Alex Turpin Nov 03 '11 at 19:01
  • @Xeon06 Oh ok, Only thing is I want allow images to be posted and links etc, So would I just need to check if the – Duncan Palmer Nov 03 '11 at 19:12
  • I would go the other way and block every tag and attribute except the ones you want to allow. This is a complicated topic, and there are many exploits available. I would suggest you research it further and look at [this question](http://stackoverflow.com/questions/4223980/php-the-ultimate-clean-secure-function). – Alex Turpin Nov 03 '11 at 19:15

5 Answers5

1
  1. I don't see any security risks with PHP code. Say, I am posting dozens of codes a day here and none of them gets excuted.
  2. Why bother of PHP tags when ordinary HTML tags are of real danger? use htmlspecialhars() to make them inactive, that's all.
Your Common Sense
  • 156,878
  • 40
  • 214
  • 345
1

There's exactly 3 ways for PHP code to get executed:

  1. run a .php script
  2. pass some text that contains PHP code through eval()
  3. include()/require() a file which contains PHP code

Having something like:

<?php 

$txt ="<" . "?php echo 'Hi mom!' ?" . ">";
echo $txt

will not magically make your browser spit out "Hi mom!". It'll spit out the PHP code itself.

If the above code were put into a file and output as follows:

$txt = file_get_contents('file_with_the_hi_mom_code.php');
echo $txt;

it would also not get executed - the user will just see some raw php code show up on their screens.

Now, if you do:

include('file_with_the_hi_mom_code.php');

or

eval (file_get_contents('file_with_the_hi_mom_code.php'));

then the code WILL be executed.

Alex Turpin
  • 46,743
  • 23
  • 113
  • 145
Marc B
  • 356,200
  • 43
  • 426
  • 500
0
  1. Why do you care about php code in textbox, can it be executed in any way?
  2. I suppose that you want to leave html tags but remove just php code (in other case you could just use strip_tags function or htmlspecialchars).

So, the solution:

<?php
//here is content from the textarea (filled it for example)
$content = 'some <?php echo "test"; ?> <?=test?> content <br/> here';

$content = preg_replace('/<\?((?!\?>).)*\?>/s', '', $content); //strip all the php code
Vitaly Dyatlov
  • 1,872
  • 14
  • 24
  • I'm worried about php because the information which they submit is displayed on another page, where the php could be executed. But thanks for the help it seems strip_tags will do the job. – Duncan Palmer Nov 03 '11 at 19:07
  • The PHP code will not be executed unless you call `eval()` on the submitted string. @DuncanPalmer .. Your first concern really should be HTML/JS (which this answer addresses). The only other freakishly corner case I could think of is taking user input, writing it to a file and then `include()` ing it, but even then, sanitizing it first applies as well. – Tim Post Nov 04 '11 at 04:49
0

Wow, lots of bad answers in here.

You don't have to worry about the user putting in PHP code. If you store it in a string and display it back, it will never get executed. You would need to go out of your way and use eval on it for that to happen. You can try it yourself:

$code = '<?php echo "hi"; ?>';
echo $code;

That doesn't do anything.

However, you need to worry about HTML.

$code = '<script>alert("hi");</script>';
echo $code;

That will work and alert "hi". To prevent that, you should sanitize everything you get from the user before displaying it with htmlspecialchars.

$code = '<script>alert("hi");</script>';
echo htmlspecialchars($code);

Here is a live example and here is a more complete answer on sanitization.

Community
  • 1
  • 1
Alex Turpin
  • 46,743
  • 23
  • 113
  • 145
-1

Foreword: this is not related only to php tags

First of all, you must decide what are the allowed character in there, and which are not. Try to limit as much as possible these (and you can check using regex).

Then, protect against XSS. Below is a piece of code used for this (as an example):

public function clean_xss($str, $charset = 'ISO-8859-1') {
/*
* Remove Null Characters
*
* This prevents sandwiching null characters
* between ascii characters, like Java\0script.
*
*/
$str = preg_replace('/\0+/', '', $str);
$str = preg_replace('/(\\\\0)+/', '', $str);

/*
* Validate standard character entities
*
* Add a semicolon if missing.  We do this to enable
* the conversion of entities to ASCII later.
*
*/
$str = preg_replace('#(&\#*\w+)[\x00-\x20]+;#u',"\\1;",$str);

/*
* Validate UTF16 two byte encoding (x00)
*
* Just as above, adds a semicolon if missing.
*
*/
$str = preg_replace('#(&\#x*)([0-9A-F]+);*#iu',"\\1\\2;",$str);

/*
* URL Decode
*
* Just in case stuff like this is submitted:
*
* <a href="http://%77%77%77%2E%67%6F%6F%67%6C%65%2E%63%6F%6D">Google</a>
*
* Note: Normally urldecode() would be easier but it removes plus signs
*
*/  
$str = preg_replace("/%u0([a-z0-9]{3})/i", "&#x\\1;", $str);
$str = preg_replace("/%([a-z0-9]{2})/i", "&#x\\1;", $str);      

/*
* Convert character entities to ASCII
*
* This permits our tests below to work reliably.
* We only convert entities that are within tags since
* these are the ones that will pose security problems.
*
*/
if (preg_match_all("/<(.+?)>/si", $str, $matches)) {        
    for ($i = 0; $i < count($matches['0']); $i++) {
        $str = str_replace($matches['1'][$i],
            html_entity_decode($matches['1'][$i], ENT_COMPAT, $charset), $str);
    }
}

/*
* Convert all tabs to spaces
*
* This prevents strings like this: ja   vascript
* Note: we deal with spaces between characters later.
*
*/      
$str = preg_replace("#\t+#", " ", $str);

/*
* Makes PHP tags safe
*
*  Note: XML tags are inadvertently replaced too:
*
*   <?xml
*
* But it doesn't seem to pose a problem.
*
*/      
$str = str_replace(array('<?php', '<?PHP', '<?', '?>'),  array('&lt;?php', '&lt;?PHP', '&lt;?', '?&gt;'), $str);

/*
* Compact any exploded words
*
* This corrects words like:  j a v a s c r i p t
* These words are compacted back to their correct state.
*
*/      
$words = array('javascript', 'vbscript', 'script', 'applet', 'alert', 'document', 'write', 'cookie', 'window');
foreach ($words as $word) {
    $temp = '';
    for ($i = 0; $i < strlen($word); $i++) {
        $temp .= substr($word, $i, 1)."\s*";
    }

    $temp = substr($temp, 0, -3);
    $str = preg_replace('#'.$temp.'#s', $word, $str);
    $str = preg_replace('#'.ucfirst($temp).'#s', ucfirst($word), $str);
}

/*
* Remove disallowed Javascript in links or img tags
*/      
$str = preg_replace("#<a.+?href=.*?(alert\(|alert&\#40;|javascript\:|window\.|document\.|\.cookie|<script|<xss).*?\>.*?</a>#si", "", $str);
        $str = preg_replace("#<img.+?src=.*?(alert\(|alert&\#40;|javascript\:|window\.|document\.|\.cookie|<script|<xss).*?\>#si","", $str);
$str = preg_replace("#<(script|xss).*?\>#si", "", $str);

/*
* Remove JavaScript Event Handlers
*
* Note: This code is a little blunt.  It removes
* the event handler and anything up to the closing >,
* but it's unlikely to be a problem.
*
*/      
$str = preg_replace('#(<[^>]+.*?)(onblur|onchange|onclick|onfocus|onload|onmouseover|onmouseup|onmousedown|onselect|onsubmit|onunload|onkeypress|onkeydown|onkeyup|onresize)[^>]*>#iU',"\\1>",$str);

/*
* Sanitize naughty HTML elements
*
* If a tag containing any of the words in the list
* below is found, the tag gets converted to entities.
        *
* So this: <blink>
* Becomes: &lt;blink&gt;
*
*/      
$str = preg_replace('#<(/*\s*)(alert|applet|basefont|base|behavior|bgsound|blink|body|embed|expression|form|frameset|frame|head|html|ilayer|iframe|input|layer|link|meta|object|plaintext|style|script|textarea|title|xml|xss)([^>]*)>#is', "&lt;\\1\\2\\3&gt;", $str);

/*
* Sanitize naughty scripting elements
*
* Similar to above, only instead of looking for
* tags it looks for PHP and JavaScript commands
* that are disallowed.  Rather than removing the
* code, it simply converts the parenthesis to entities
* rendering the code un-executable.
*
* For example:  eval('some code')
* Becomes:      eval&#40;'some code'&#41;
*
*/
$str = preg_replace('#(alert|cmd|passthru|eval|exec|system|fopen|fsockopen|file|file_get_contents|readfile|unlink)(\s*)\((.*?)\)#si', "\\1\\2&#40;\\3&#41;", $str);

/*
* Final clean up
*
* This adds a bit of extra precaution in case
* something got through the above filters
*
*/  

$bad = array(
        'document.cookie'   => '',
        'document.write'    => '',
        'window.location'   => '',
        "javascript\s*:"    => '',
        "Redirect\s+302"    => '',
        '<!--'          => '&lt;!--',
        '-->'           => '--&gt;'
);

foreach ($bad as $key => $val)  {
        $str = preg_replace("#".$key."#i", $val, $str);
}

return $str;

}