FRIHOST • FORUMS • SEARCH • FAQ • TOS • BLOGS • COMPETITIONS
You are invited to Log in or Register a free Frihost Account!


How To : Secure Your PHP Website






Did this help you at all ?
Yes, Definately.
75%
 75%  [ 73 ]
No, It Did Not.
24%
 24%  [ 24 ]
Total Votes : 97

izcool
Hey everybody,

You probably noticed me floating around these forums. I wrote another "How To" related to PHP Programming. Since I have nothing else better to do at the moment, I feel like writing another tutorial, one on Securing Your PHP Website.

Here it goes, I hope everyone reading learns a thing or two. Please participate in the Poll in this Thread, to tell me if this tutorial helped you or not. Smile

1 - ALWAYS, and I mean ALWAYS use $_GET and $_POST variables
I've been programming PHP ever since the start of last year. I've learned a lot from then, and the thing that I would like to stress the most is to ALWAYS use $_POST and $_GET variables when you are using some kind of a form, or if you're grabbing information from the trail end of the URL. I hate to admit it, but before I learned about $_POST and $_GET, I used to program very "unsecurely" by not using $_POST and $_GET. In order for $_POST and $_GET to work in a form, you need to set the method= attribute to GET or POST, depending on what you're going to use later on to process the code. You can only use $_GET if you want to collect information from the trail end of a URL. For instance, the URL on the page I'm making this post on, there are two variables that are more than likely using $_GET. "mode" and "p". I can't go on forever explaining how to use $_POST and $_GET, but I do recommend you to read a PHP book or check-out the wonderful documentation available for free at PHP.net. If you use variables without $_POST or $_GET around them (again, when you're collecting information from a form or from the trail end of a URL), you're waiting for disaster to happen. I used to own a gaming site, a very popular one. I soon found out that hackers were using home-made programs in order to "cheat" my web game because I wasn't using $_POST or $_GET. For instance, if you made your own forum without using $_POST or $_GET, hackers can take a few minutes to make a program to flood your forum in a matter of a few seconds. What's even worse is that it's easy enough to do it in PHP. I won't post the code here as I think people might use it to their advantage. Avoid this and your website should be fine. I just remembered, I wrote a tiny code awhile back that prevents most home-made programs from attacking your website. Place this near the top of your layout file and you should be pretty secure. Good luck with it. Smile
Code:

if((getenv("HTTP_USER_AGENT") == "Microsoft URL Control - 6.00.8862") || (getenv("HTTP_USER_AGENT") == "Microsoft URL Control - 6.00.8169")){
exit;
}


2 - ALWAYS, and I mean ALWAYS error check EVERYTHING
I recommend you to read my PHP "How To" if you haven't done so already. A few of the things I cover in there are related to error checking. I do recommend you to use error checking codes on MySQL connections/queries, any form processing code (such as if everything that you require was filled in, if a digit box is only digits, etc), and including if you are including files into your scripts. I do recommend you to use user-friendly error codes, because a visitor might run into one and may be a little confused if they see "Error 23". Instead, you could probably use "Error 23 - You forgot to enter your password". The #23 might be used for the programmer to see what could be wrong if they test their code before public use.

3 - Securing your if-then statements
This one is overseen by most people, but I sometimes like to secure my if-then statements even more. For instance, let's say that your site has a "Free Account" level and an "Advanced Account" level. Let's say that you're restricting Free Accounts from accessing the Advanced Account benefits. You set up an if-then statement that is simply put "If the user account is a free account, stop them from accessing this page, display this message, and stop the page load". This could look something like :
Code:

<?php
$level = "Free Account";
if($level == "Free Account"){
exit("Your account is not an Advanced Account, so therefore you cannot access this page.");
}
// Actual content for Advanced Accounts shows up here //
?>

You could secure this even more by doing this instead :
Code:

<?php
$level = "Free Account";
if($level == "Free Account"){
exit("Your account is not an Advanced Account, so therefore you cannot access this page.");
}else{
// Actual content for Advanced Accounts shows up here //
}
?>

Only a few key taps, and you've secured your if-then statement even better. This is good because you know that it's secure and they're not going to access what don't want them to.

4 - Restricting access to hidden folders
This I've seen a few times on some sites. They (like most sites) have images stored away in a separate directory. But, what they don't know is that the directory can be easily accessed where you can see what's inside it by a default Index page from Apache (on an Apache server of course, and no user-made Index file is made, too). If this isn't turned off by default, you can create a file named ".htaccess" (no quotes, and including the . before htaccess) and have this inside it :
Code:

Options -Indexes

This will show a page that denies access to the directory. If (for some reason) you want to see what's in the directory through that default Index file, you would pretty much do the opposite in the .htaccess file :
Code:

Options +Indexes


5 - Securing your secure admin area
One of the things that people forget to do on their website is blocking out the riff-raff from accessing their precious admin areas. Choose difficult passwords (most of mine are all random letters and numbers) that are hard for password cracker programs to choose from a list. I have seen many programs that try to hack through FTP accounts. They have huge dictionaries of passwords that worked on other sites that get hacked. By me looking in a few of them, they don't bother to try random passwords like "3qrfdsgsdf44w", as that would take forever to do. This should go for caution for sites with a cPanel control panel, a hacker could easily get the UserName for the cPanel account by looking around the site for any errors with PHP programming. For example :
Code:

Parse error: parse error, unexpected T_IF, expecting ',' or ';' in /home/somesite/public_html/test.php on line 6

As you can see above, "somesite" is the username on the cPanel account. Try to eliminate all test files and errors on your website so that no one can try to hack into your files and databases.

6 - Preventing JavaScript Hijacking
This is one of the most ingenious ways of hacking on websites that I've ever had to encounter. About a year and a half ago, I found out that one of the players on my gaming site was stealing the cookie information that I was using to keep users logged into their accounts. I could not understand how this one user made it possible, but I had researched the situation and found out exactly how he did it and how it worked. Basically, the user put a JavaScript snipplet on his user profile (I had accepted HTML and JavaScript in user profiles on my gaming site), which was grabbing the user's cookie information on the gaming site, the JavaScript code redirected the user to an external website (to a PHP page), and from the PHP page, the data that was collected from the JavaScript cookie code was either eMailed to the hacker or inserted into a MySQL DataBase, I'm not sure which, but it could have been either of them. With the cookie data that he literally stole from someone else's computer (with someone else's username and password in the cookie), he changed HIS cookie information to the one that was eMailed to him, and went to my gaming site. BOOM ! He was in. The only ethical way of stopping this from happening (while accepting HTML and JavaScript) I had blocked out the cookie name that I was using on my site, so that it could not be collected through that JavaScript code. Yes, it may sound very shallow, but it was one of my biggest concerns at one point in time.

7 - Preventing SQL/URL Injection
This will only occur when you do not use $_GET or $_POST variables when you are collecting data from a form or at the end of a page URL. I highly stress using $_GET and $_POST variables, as described in the first tip. SQL injection is where additional data is added at the end of a form field box, and updates other information in the database, perhaps some data that was not supposed to be edited. URL injection is the same and can work different too. Sometimes, you can enter in bits of data at the end of the URL to change some of the programming around, muffing up your programming and allowing hackers to really mess up your database info.

8 - Never Use Sessions !
When I was first developing my popular gaming site a few years ago, I started to use sessions to log users into their accounts, instead of cookies. I found out very quickly that sessions are not what they're meant to be. Apparently, it was swapping user data from one computer to another, and not directing the session data to the correct computer it was meant to go to. For instance, the user "admin" could be swapped with someone else like "blacktopbandit", which can cause a serious problem. I recommend to use cookies HIGHLY over sessions, due to that concern.

9 - Securing Your Cookies
As mentioned in the tip above, I recommend that you use cookies instead of sessions. There can be a variety of concerns with cookies too, but you can secure them by encrypting the data that's inside them. I recommend using the md5() and base64_encode() encrypting methods for cookies (better if both are used). When I did my gaming site, I left the username unencrypted, and let the password be encrypted with the above methods. One thing that most people forget to take into consideration is by checking the cookie data on EVERY page load, to see if it is legit. Check the username, the password (using the encrypting methods as well), and other data that you might have in the cookie as well.

10 - Use Image Verification On Registration Forms
When I had owned my gaming site awhile ago, I found out that bots were crawling my site and registering fake accounts, clogging up the database. To prevent this, I recommend using Image Verification, if your server supports it. In order to use PHP images, you need something called the "GD Library" enabled. If it is not enabled (you can check by running the phpinfo() command on a test page), then ask your web host if they can enable it for you. This eliminated all the bots that were registering fake accounts.

11 - Ask For Help If You Need It !
There are many forums that you can go to, such as :

- SitePoint Forums (http://www.sitepointforums.com/)
- ProgrammingTalk (http://www.programmingtalk.com/)
- FriHost Foums (http://www.frihost.com/forums/index.php)

Basically, post your concerns with your website security, and post some samples of your code if you feel that it is necessary. More than likely, there will be someone that will be more than willing to help you out and get your site in better shape.

12 - Read Security Tutorials
There are many good tutorials on the web that you can check-out if you are unsure that your PHP website is secure. This thread only covers a few topics and concerns, though there may be other things to be considered as well. Surf Google for awhile and I'm sure you'll come up with quite a few.

Hope I've helped.

- Mike.
Cerb
I'd like to point something out in #7:

Some sites tend to use dynamic URLs like ?file=something.php
I think that whoever uses this kind of file inclusion should check if the file belongs to the website with HTTP variables to make sure what is included is not an external file, which could contain malicious code.
newaira
I recommend using SafeSQL for creating SQL queries. It will take care of security issues such as SQL injections and make your queries/scripts easier to read.
phervers
Well with some things i do agree with some i do not.
point 3.
both code snippets do the same thing ! there's nothing in it about security. Also it would be better to check like that
Code:

<?php
$level = "Free Account";
if($level != "Advanced Account")
{
   exit("not Advanced");
}
else
{
   //Advanced content
}
?>


otherwise if you would mistype your var like for example
Code:

$level = "Fre Account";

your code would give user access to advanced functions.

Optimally you should use define's like
Code:

<?php
define("UL_FREE",         "Free Account");
define("UL_ADVANCED", "Advanced Account");
?>

then you can use
Code:

<?php
$level = UL_FREE;
if($level != UL_ADVANCED)
{
   exit();
}
else
{
   //Advanced
}
?>



Point. 8
Seems like a lot has changed since that time cause sessions are generally more secure than cookies. Cookies are much easier to intercept for a potential hacker because they are stored on client machine not on your internet server. The situation you described in point 6 would not happen if you would use session variables for storing user data. (allowing users to add own javascript to your site is a serious security threat itself). When using sessions only thing which can be stolen is session_id which is valid for only a limited time. Sessions are still not completely secure because of that threat (session hijacking), but you can make them quite secure using some techniques like asking user for old password when setting new one, when displaying credit card info only display last 4 digits etc.. Cookies are useable for long-term info storage like remember-me checkboxes not for storing temporary info used when user is logged in.
simplyw00x
Not meaning to rain on your parade, but this is some pretty shoddy security advice. You mention 'Always use GET and POST' (as opposed to what?), but then say 'Beware of mySQL injection'. Consider the following:
Code:
<?php
$pass = $_POST['pass'];

$sql = mysql_query("SELECT user FROM users WHERE pass = '$pass'");

//etc...
?>


Now, all someone has to do is enter '0 OR =''' as their password and they're laughing. Obviously a simplistic example, but there you go.

Also, that IF THEN ELSE statement is only more secure in the second id register_globals is on, which it hardly ever is, and definitely isn't on Frihost.
charliehk
So how could you solve the problems?
izcool
Well to answer your question, the register_globals needs to be enabled in order for that to be a problem (on every other webhost I've been on they've been turned on).

For instance :

Code:
<?php
if($pass == "something"){
echo"You're in";
}
?>


Someone could just go to the page with ?pass=something at the end of the URL and they're in. The reason why I urge $_GET and $_POST is because that's a much better way about going around that. I recommend $_POST for forms and $_GET for end-of-url type of stuff.

I do understand that you had a dispute about the $_POST and $_GET thing, but I wrote this tutorial in efforts of helping novice programmers with security and improving their PHP scripts. Most of the stuff that I've mentioned in my tutorial above are things that were a problem/concern for me in my days of programming.

As with SQL injection, if the programmer programs the code incorrectly, naughty visitors could add bits of information after their form data and screw up the database, as so :

Name: [ Mike', 'something else to throw off the database ]

- Mike.
simplyw00x
Quote:
I do understand that you had a dispute about the $_POST and $_GET thing, but I wrote this tutorial in efforts of helping novice programmers with security and improving their PHP scripts. Most of the stuff that I've mentioned in my tutorial above are things that were a problem/concern for me in my days of programming.

I have no beef with GET and POST, I'm saying there's no alternative anyway and it's still insecure, hence why bother posting it?

If your index.php chooses a section like 'index.php?s=1' then that is a GET variable. The only way to get the value of 's' in that instance is from GET, unless $register_globals is on, which it usually isn't.

And yes, I know how injection works. Other people don't, so posting 'beware of mySQL injection' could at least go with a link to dealing with it.
izcool
Since you're pointing out to post a link on how to prevent SQL injection, why not you go and suggest one since you had mentioned it ?

- Mike.
charliehk
I agree that some resource links are helpful!

Also, I agree with the other nine who vote that this post is not meaningless. It is indeed useful.

Of course, if how to deal with SQL injection is mentioned, we will benefit more!
lingcj
simplyw00x wrote:
Quote:
I do understand that you had a dispute about the $_POST and $_GET thing, but I wrote this tutorial in efforts of helping novice programmers with security and improving their PHP scripts. Most of the stuff that I've mentioned in my tutorial above are things that were a problem/concern for me in my days of programming.

I have no beef with GET and POST, I'm saying there's no alternative anyway and it's still insecure, hence why bother posting it?

If your index.php chooses a section like 'index.php?s=1' then that is a GET variable. The only way to get the value of 's' in that instance is from GET, unless $register_globals is on, which it usually isn't.

And yes, I know how injection works. Other people don't, so posting 'beware of mySQL injection' could at least go with a link to dealing with it.
digibluez
The 1 post was some kind of use,there a relots of php sites to look such info at.I am just a beginner at php,but i want to learn more.As i almost know all i want from html-graphics.Now its time for programming.

http://www.phpfreaks.com/forums/

a simple sql injection protect.
http://www.cback.de/cback_software/standalonect.php
charliehk
Just include one statement

include "ctracker.php";

and that's it? I don't know since it is not in English.
digibluez
yes just include it or copy it to your functions file,you can still add more lines to secure.Like try google.
lolindir
Very very useful indeed but I didn't really get why you insist on not using sessions. You can encrypt them too, which makes them secure.
friscofrankie
izcool wrote:

1 - ALWAYS, and I mean ALWAYS use $_GET and $_POST variables


just curious; as opposed to what?
You go on to say youve been programming PHP for maybe, a year-and-a-half. That's sending BS alarms to my brain already, but like I train wreck I can't pull my eyes away...
Quote:

2 - ALWAYS, and I mean ALWAYS error check EVERYTHING
I recommend you to read my PHP "How To" if you haven't done so already.


And where might that be?
Quite frankly there are more Tuts out there than you can shake a stick at. But by all means, please, post a link I believe that you can learn from anyone; I'm sure in your time writing PHP code you have resolved issues that I may yet have to face. Always interested

Quote:

3 - Securing your if-then statements
This one is overseen by most people, but I sometimes like to secure my if-then statements even more.
Code:

<?php
$level = "Free Account";
if($level == "Free Account"){
exit("Your account is not an Advanced Account, so therefore you cannot access this page.");
}
// Actual content for Advanced Accounts shows up here //
?>

You could secure this even more by doing this instead :
Code:

<?php
$level = "Free Account";
if($level == "Free Account"){
exit("Your account is not an Advanced Account, so therefore you cannot access this page.");
}else{
// Actual content for Advanced Accounts shows up here //
}
?>



Have to agree with another poster; what's the difference in those two snippets?? Even more to the point. What does this do that any authentication algorithm wouldn't do. how is this securing the if statement itself? This is only"if(authenticated) {OK} and nothing more, sorry, but where's the beef?

You go on to tell us cookies are more secure than sessions? If you're going to write a tutorial I believe that is incumbent upon the author to check and recheck data anecdotal data is not really that concise, and "it happend one time to me" is hardly a reason for eveyone to abandon what appears to be a much more secure method due to your probelm. If you were to have phrased this not as a tutorial but as an opinion with anecdotes it could have started a dialog that could have been useful to beginner, experts and everyone in-between.

After this point you lost me. This is not a tutorial. It does bring to light many possible security pitfalls to avoid. However, it gives no real advice or pointers to real tutorials on how to avoid them.
In my opinion this was of very little use. Some stuff was right on but too general to be considered a tutorial. For a beginner it may be like saying, "Hey it's a tough world out there and you better be prepared!!" without giving one iota of advice on how to prepare.

fairly well written though, readable. Now give us the beef!!
I would enjoy readng more anything of you write
Would be very interested in how the hijacking was done; with info like that I guy could harden his site against such an exploit or at least know if he was vulnerable. This could easily be done without dumping the code out for script kiddies to cut and paste while giving some insights on how to combat it. It could also give some the newbies out there an opportunity to gain knowledge from more experienced coders as they discussed the manner is which the exploit could be prevented.

If the poll had a few more choices I'd give this write-up a couple points but you've only given us pass/fail alternatives.

Fail.

FF
izcool
I appreciate and respect everyone's comments.

In regards to friscofrankie's reply right above mine :

I recommend to use $_GET and $_POST as opposed to just the stripped-down variables, like $page. Most web servers don't enable the support for those if you are collecting from the address bar or from a form, so, use $_GET[page] or $_POST[page] instead. It is much more secure and the proper way of doing it.

The difference between those 2 snipplets is that you have one way to back up if something fails. If you only put a door lock on a door in the city, that's not always going to be the best. You're going to want to put a deadbolt lock added with that to make sure that it's more secure, that's the reason why I stress that. If the exit() command in that code snipplet does not work, then it is backed up by using the else{} possibility. It cannot hurt to add that extra little security feature in there, can it ? All you can lose is only a few kilobytes of disk space, but I would rathar use the space to make my sites more secure.

I've had bad experiences with sessions (I've used them before cookies) because the sessions were getting overlapped from one computer to another. For instance, I was running a game site a few years ago which required a login system for user accounts. I used sessions at first, but I was getting stuff for other people's accounts instead of my own. I recommend cookies because they're easier on the user (instead of logging in every hour), but they need to be coded properly otherwise they will be a big threat to your website.

Many people look at my list of suggestions to be aware of when programming PHP differently. Some people reading may have learned a thing or two from my experiences with my own programming. Others who may surpass my programming skills may look down at this in shame. But you have to remember that programming is tough and it can be a huge nightmare if it is not worked with properly. I have learned PHP and HTML on my own by reading through other people's codes and winging it. I have not taken any classes or read through entire books on how to do it properly, so that might be my fault. I'm sorry if it is. I'm sorry if I've disappointed you in this tutorial. Please try to look at the best side of things and suggest a few things if you would on top of what I have instead of saying that this is rubbish. To me it isn't.

- Mike.
friscofrankie
PHP is rather simple language to learn and a logical choice for beginners. Most of the hard work has been done in the language and it makes it easy for folks to get trapped into many of the pitfalls you mentioned. for that it does have merit.
Perhaps I was a bit overly optimistic. I started coding in 1984 on an 808x usining a tape drive! Not much was available in way of high level languages then. I never accepted a job as programmer but went, instead, the route of systems engineer. My last job was as systems/security architect. Of course in those roles you still code (some, quite a bit; others, not so much) but you are not locked to a desk coding all day. Most of my work was at a systems level.
Most of my web script work has been in Perl, a lot of what was done in these intranet solutions was binary CGI as well. In my career I've used several flavors of basic, c, C++, asm, Pascal, SQL, Xbase, several permutations of Java, Fortran, RPsomething for the AS400, and others I'd learn for a week to get a job done then forget I ever knew.
I am also learning PHP by reading scripts and some online resources. I find it overly simple and a quick solution for rapid development. the language is quite intuitive For my first attempt I am just finishing up a database/catalog app.
When I looked at your post I had hoped for some real, down and gritty, security advice I cold apply to my current situation. Perhaps I set the bar a bit too high. Where your target audience was the neophyte, I was looking forward to some real nuts & bolts.
As I wrote before, I would be most interested to read anything you wrote. You have a readable style; some more 'in depth' coverage of your trials and tribulations would be welcome by the neophyte and the experienced coder alike. You might also get some input as to other solutions you didn't think of at the time.
We can all learn from each others mistakes. Wink
Now, back to that !@#&%$ databse. Easy enough, but boring.
izcool
Well that goes to show everyone, you've been programming longer than I've been alive. Laughing I was born in 1989.

My programming days are near to it's end, I've started HTML in 2001 in interest and moved onto a more complicated programming language (PHP) to expand my horizons.

PHP is quite different than HTML, so it would be hard for beginners to pick it up. Other server-side languages to PHP might have the same roots and might be easier to work with if you know other languages similar to PHP. I'm currently in a Website Design class in my school, the first thing we did was a small intro to HTML (many kids were getting lost with HTML as most of them haven't done it before), so I can only imagine they would have the same feeling (maybe worse) if they were to try to do PHP. I took the class because I wanted to fill in my gaps about the web and get an easy credit. Razz

- Mike.
charliehk
friscofrankie wrote:
PHP is rather simple language to learn and a logical choice for beginners. Most of the hard work has been done in the language and it makes it easy for folks to get trapped into many of the pitfalls you mentioned. for that it does have merit.
Perhaps I was a bit overly optimistic. I started coding in 1984 on an 808x usining a tape drive!
...
Most of my work was at a systems level.
Most of my web script work has been in Perl, a lot of what was done in these intranet solutions was binary CGI as well. In my career I've used several flavors of basic, c, C++, asm, Pascal, SQL, Xbase, several permutations of Java, Fortran, RPsomething for the AS400, and others I'd learn for a week to get a job done then forget I ever knew.
I am also learning PHP by reading scripts and some online resources. I find it overly simple and a quick solution for rapid development.
...

Interesting! I think we are two of the very few here that had used AS400 before. And I have shown my respect when I read your post since most of those who wrote RPG and Fortran won't be able to learn Java and PHP, so you must be very smart.

btw, why didn't you start programming w/ Apple IIe compatible? Smile
Positron
u cant edit massage on your script error

Code:
set_error_handler("your_fonction");


function your_fonction($type, $message, $file, $line, $context){
   $debug_state = "ERROR";

   switch($type){
      case E_NOTICE:
         echo "<font style='font-family:\"ms Sans Serif\"; font-size:10px; color:#000000'><b>Notice:</b> ".$message.", Line <b>".$line."</b> of <b>".$file."</b></font> <br />";          
      break;
      case E_WARNING:
         echo "<font style='font-family:\"ms Sans Serif\"; font-size:10px; color:#000000'><b>Warning:</b> ".$message.", Line <b>".$line."</b> of <b>".$file."</b></font> <br />";
      break;
      case E_ERROR:
         echo "<font style='font-family:\"ms Sans Serif\"; font-size:10px; color:#000000'><b>ERROR:</b> ".$message.", Line <b>".$line."</b> of <b>".$file."</b></font> <br />";
      break;
      default:
         echo "<font style='font-family:\"ms Sans Serif\"; font-size:10px; color:#000000'><b>ERROR: </b>".$message.", Line <b>".$line."</b> of <b>".$file."</b></font> <br />";
      break;
   }
   if(eregi("ECHOSTATE", $debug_state)){
      echo "<br /><font style='font-family:\"ms Sans Serif\"; font-size:10px; color:#FF0000'>Variable state when error occurred: </font> <br>";
      print_r($context);
   }
}
jasperlevink
izcool wrote:

Code:

if((getenv("HTTP_USER_AGENT") == "Microsoft URL Control - 6.00.8862") || (getenv("HTTP_USER_AGENT") == "Microsoft URL Control - 6.00.8169")){
exit;
}



I don't really understand what you're doing here??
Grtz.
jasperlevink
I don't really understand how using $_POST and $_GET can prevent SQL injection. People can still enter information in the forms to alter the SQL query?
jasperlevink
What if cookies ar unabled?
phervers: What's the define command?

This is the crackertracker code mentioned bu digibluez:
Code:
<?php

// Cracker Tracker Protection System
// Created by: Christian Knerr - www.cback.de
//
// License: GPL
//
//
// Begin CrackerTracker  StandAlone
//

  $cracktrack = $_SERVER['QUERY_STRING'];
  $wormprotector = array('chr(', 'wget', 'cmd=', 'rush=', 'union', 'UNION', 'echr(', 'esystem(', 'cp%20', 'mdir%20', 'mcd%20', 'mrd%20', 'rm%20', 'mv%20', 'rmdir%20', 'chmod(', 'chmod%20', 'chown%20', 'chgrp%20', 'locate%20', 'grep%20', 'diff%20', 'kill%20', 'kill(', 'killall', 'passwd%20', 'telnet%20', 'vi(', 'vi%20', 'INSERT%20INTO', 'SELECT%20', 'nigga', 'fopen', 'fwrite', '$_REQUEST', '$_GET');
  $checkworm = str_replace($wormprotector, '*', $cracktrack);

  if ($cracktrack != $checkworm)
    {
      $cremotead = $_SERVER['REMOTE_ADDR'];
      $cuseragent = $_SERVER['HTTP_USER_AGENT'];

      die( "Attack detected! <br /><br /><b>Dieser Angriff wurde erkannt und blockiert:</b><br />$cuseragent" );
    }

//
// End CrackerTracker StandAlone
//

?>


I don't really understand what it does.

As you might see is that i'm not yet a professional PHP programmer. I hope someone can help me with my problems.

Grtz.
Jasper
izcool
Basically, if you don't use $_POST and $_GET correctly, a bot can generate thousands of different queries and run them through a shell command (or something) to load up the database with random information made by computer. I didn't mention that before, but Image Verification is one of the best options people should use if you are making a registration form of some sort. Normally computers cannot detect the letters if there are random backgrounds behind the lettering, so that will prevent bots from making such drastic actions. $_POST basically represents that it has to be entered within a form (most of the time, unless if you use a hacking program to make it seem like it's coming from a form), and $_GET generally indicates that you're collecting data from the end of the URL. For instance, in the page that I'm looking at, the $_GET variables would be "mode" with the value of "reply", and "t" which would have the value of "4587".

Thanks for sharing that small tool try to prevent SQL injection. SQL injection is where people use the $_POST and $_GET operations if they are not coded properly to make the database thinking into doing operations that aren't meant to be. For instance, you could have a variable that is your query :

Code:

<?php
$query = "INSERT INTO table (name) VALUES ('$_POST[name]')";
mysql_query($query) or exit(mysql_error());
?>


Someone could get around that by adding ?query=DELETE FROM table at the end of the URL to do an operation that isn't meant to be programmed to do. $_GET over-rides the line-by-line code, so be careful.

I would recommend $_POST for forms as it would be very hard to recreate that form to make it work with SQL injection. There are ways but they're difficult to manipulate with. I would only use $_GET if you are collecting information to be pulled from the database, like in a forum, when you are reading a thread or something.

I know all this because I've had many hacking attempts on the gaming website I used to own and operate a few years ago.

I'm sorry if I haven't made this point clear before, but that's basically (in rough terms) on what it is.

- Mike.
ammonkc
I didn't realize that there was an alternative to $_GET and $_POST variables, besides maybe $_REQUEST. what is the unsecure method to pass data with forms?

phervers posted something about defining your variables first to secure them. can somebody explain what exactly define() does.
Code:
<?php
define("UL_FREE",         "Free Account");
define("UL_ADVANCED", "Advanced Account");
?>


I'm really not too clear on how define() is different from a regular variable declaration. thanks
sonam
Define is constant but not variable. here is what I find.


Code:
A constant is essentially a value that cannot be modified throughout the execution of a program. Constants are particularly useful when working with values that will definitely not require modification, such as pi (3.141592), or a specific distance such as the number of feet in a mile (5,280). In PHP, constants are defined using the define() function. Once a constant has been defined, it cannot be changed (or redefined) at any other point of the program.

Pi could be defined in a PHP script as follows:

define("PI", "3.141592");

And subsequently used in the following listing:
print "The value of pi is". PI.".<br>";
$pi2 = 2 * PI;
print "Pi doubled equals $pi2.";
producing:

The value of pi is 3.141592.
Pi doubled equals 6.283184.

There are two points to note regarding the previous listing: The first is that use of a constant does not require a dollar sign. The second is that it’s not possible to modify the constant once it has been defined (for example, 2*PI); if you need to produce a value based on the constant, the value must be stored in an alternative variable.


Sonam
Grimboy
This is good, but to the guy who wanted the "beef". Theres some slightly more substantial stuff here > http://www.sklar.com/page/article/owasp-top-ten.
DX-Blog
izcool wrote:
I would recommend $_POST for forms as it would be very hard to recreate that form to make it work with SQL injection. There are ways but they're difficult to manipulate with. I would only use $_GET if you are collecting information to be pulled from the database, like in a forum, when you are reading a thread or something.

I would recommend not teaching people complete BS. Whether you use $_POST or $_GET it doesn't matter, using SQL injections is just as easy. Instead of knowing this by working on some corporate gaming site this knowledge came by a fun battle with a friend in which we tried to constantly take down eachothers sites to increase our knowledge when it comes to site security.

Now if some high school student like me, which does this like a hobby, can use SQL injections on $_POST statements, how easy would you think it is for a real hacker to take your entire site down that way?

Instead you should always, and I can only repeat this ALWAYS, secure your data by 'cleaning' it first. Whether you use $_GET or $_POST, this is just a must you should not forget otherwise you might get yourself in some nice trouble.

You can see an example on the following page:
http://www.askbee.net/articles/php/SQL_Injection/sql_injection.html

This just offers a minor check though, you will always be wanting to check certain values specifically as well. Like usernames to contain only alphanumerical characters and perhaps an underscore, passwords to allow alphanumerical characters and certain special symbols like $.

Basically you are preventing a possible SQL injection at 2 points, through your cleaning method and through your variable validation method. If you do this correctly then SQL injections are near to impossible, remember though, it will never be completely impossible seeing as to how dynamic PHP is.

The true difference between $_GET and $_POST is that if you use it right all data you pick up with $_GET comes through HTTP GET, these are things which are in example passed on through the URL of your page.

This should only be used for reading information, not to make any adjustments. You should not create a link with:
admin.php?delete=post&id=3 in example.

Fun to have something like that, not the way to go. If someone is prefetching pages with in example google web accelerator the link will be prefetched, script excecuted and gone is your post without you wanting it.

$_POST on the other hand works through HTTP POST, which is only coming through the processing of forms. To prevent security risks as told earlier you will have to check whether there was actually a submit, but in general this is more secure against prefetching and all.

There are some other factors playing a role as well, you can read a lot of this back on php.net when it comes to $_POST and $_GET, but the main importance is that you should remember that you should use them at the right time and of course, never forget to clean the data first before actually processing it.

As for the person which brought up $_REQUEST, you should avoid this at all time. This gathers info throughout the POST, GET and COOKIE input mechanisms. It basically is a 'I dont know what to do so lets throw em all in' function, when it comes to security though that's like the worst you can do.

As for the sessions/cookies thing, there is no best in them. Both have their pro's and both have their cons. If you use them right though and the server settings are correct the chance of them causing trouble is minimal. The moment you start giving on session data in URL's though or you don't encrypt your cookies you're already starting to get yourself in trouble. But you can make it even worse Razz.
1money69
Posted: Thu Sep 29, 2005 12:57 am Post subject:

--------------------------------------------------------------------------------

I appreciate and respect everyone's comments.

In regards to friscofrankie's reply right above mine :

I recommend to use $_GET and $_POST as opposed to just the stripped-down variables, like $page. Most web servers don't enable the support for those if you are collecting from the address bar or from a form, so, use $_GET[page] or $_POST[page] instead. It is much more secure and the proper way of doing it.

The difference between those 2 snipplets is that you have one way to back up if something fails. If you only put a door lock on a door in the city, that's not always going to be the best. You're going to want to put a deadbolt lock added with that to make sure that it's more secure, that's the reason why I stress that. If the exit() command in that code snipplet does not work, then it is backed up by using the else{} possibility. It cannot hurt to add that extra little security feature in there, can it ? All you can lose is only a few kilobytes of disk space, but I would rathar use the space to make my sites more secure.

I've had bad experiences with sessions (I've used them before cookies) because the sessions were getting overlapped from one computer to another. For instance, I was running a game site a few years ago which required a login system for user accounts. I used sessions at first, but I was getting stuff for other people's accounts instead of my own. I recommend cookies because they're easier on the user (instead of logging in every hour), but they need to be coded properly otherwise they will be a big threat to your website.

Many people look at my list of suggestions to be aware of when programming PHP differently. Some people reading may have learned a thing or two from my experiences with my own programming. Others who may surpass my programming skills may look down at this in shame. But you have to remember that programming is tough and it can be a huge nightmare if it is not worked with properly. I have learned PHP and HTML on my own by reading through other people's codes and winging it. I have not taken any classes or read through entire books on how to do it properly, so that might be my fault. I'm sorry if it is. I'm sorry if I've disappointed you in this tutorial. Please try to look at the best side of things and suggest a few things if you would on top of what I have instead of saying that this is rubbish. To me it isn't.
Mgccl
What. No session?????
that's just unbeliveable......
then when people disable cookie, what can anyone do?
sessions is the way that keep the users safe....(less cookie)
and less info send back to the server(don't need to send cookie info)
DoctorBeaver
AS400... those were the days. I also had the misfortune to work on DataGeneral Novas & IBM 360s.
ccarter24
I uses SESSION variables in every page. I've never had a problem with it. On my logon page I set an authenticates variable, and then check for it being set at the top of every page. If it's not set, the user is bounced back to the Logon page. But that's me.
martindecorte
izcool wrote:
I recommend using the md5() and base64_encode() encrypting methods for cookies (better if both are used).

Well, I went once to a "Security Day", where Mrs Rafal Lukawiecki and Jesper Johansson were having speech about computer security.

Rafal talked about encryption, and told us something he called "one of the most important things": NEVER try to make better than the existing algorithm, be it ancryption or hash.

He explained like this: "it's not your job to make powerful and solid algorithms, it's mine ; and if you try to improve an algorithm on your own, you could actually totally break its reliability". That is mainly true if you want to use twice the same algorithm, thinking you'll encrypt your password twice better ; but it's also true when you combine algorithms.

There are (very) difficult mathematical research, evaluating algorithm's reliability, and you aren't sure at all that if you combine 2 algorithms, you'll get a good security.


So, I'd never combine 2 hash algorithms, since this Rafal told me not to do (and he's an expert).
Saryon
Thanks, it's realy usefull. I'm still learning PHP, and I can use everything I can get my hands on Very Happy
adam.eickhoff
Thanks for this informative article. I have never coded in PHP before but I know the basics of coding in general. Also, this is part of the reason I would love to become a hostee on this site; I need the PHP web hosting support. I can set up servers with PHP/perl/ASP support but my bandwidth is dial-up and thats no good. AND THE HOSTING IS FREE! another plus.
aciminsk
Am reading "PHP 5 Power Programing" by Gutmans, Bakken and Rethans. Chapter 5.4 "Safe handling user input" goes OK, I understand what's the talk is about. Chapter 5.5 "Techniques to Make Scripts Safe" starts OK also. But when reading 5.5.2 HMAC Verification and 5.5.3 PEAR :: Crypt_HMAC, getting somewhat lost. Would appreciate if somebody coulld point me to a newbie-friendlier description of these solutions.
Philip
How about make it like this one ?
Code:

<?php
$name=mysql_real_escape_string($_GET["name"]);
$query = "INSERT INTO table (name) VALUES ('".$name"')";
mysql_query($query) or exit(mysql_error());
?>


will it make more safety ?
BruceTheDauber
My suggestion for PHP security is to do all the processing of the request in one location, and not let any other parts of your code (especially SQL queries) see the request data.

You could do, e.g.,

Code:

function handle_request()
{
  // process all the anticipated variables, making sure everything is initialized:
  $userauth = isset($_SESSION["foo"])?base64_decode($_SESSION["foo"]):"";
  $forminput = isset($_POST["bar"])?$_POST["bar"]:"";
  $forminputnumber = isset($_POST["num"])?(int)$_POST["num"]:-1;
  //etc.

  // now validate each variable, checking for hacks:
  if ($forminput == "") {
    // invalid input
  } elseif ($forminput != strip_tags($forminput)) {
    // this input shouldn't have tags in it, so we've probably spotted a hack!
  } elseif ($forminput != mysql_real_escape_string($forminput)) {
    // another probable hack!
  } else {
    // whatever
  }

  // there might be some other checks you can do, e.g.:
 if ($forminput == "x" && count($_POST) != 3) {
   // something's wrong, and it might be a hack
 }

 $whatever = decide_what_to_do($userauth, $forminput);

 // only now do you call the code that will do database queries and
 // generate pages:
 switch($whatever) {
 case "a": update_bank_account_details($forminput); break;
 case "b": update_medical_records($forminput); break;
 case "c": send_a_message_to_the_secret_service($forminput); break;
 default: show_default_page();
 }
}


If you follow a pattern like that, it will be harder for you to forget to check something.

I think.
deathwingpnx
Good code, this one prevents attacks from $_GET variables by using $SERVER['QUERY_STRING']. Another good one should be preventing sql inserts having javascripts codes such as <script, language='javascript', </script> and so on.

Hmmm... I think there has been a redirection problem.

My reply should be in http://www.frihost.com/forums/vt-4587.html

Strange.
Ka7raK
Another good how-to but i don't agree with the anti-session statements.
chrismen
Both your tutorials are great and have helped me a lot but can you explain what exactly the code under number 1 does?
AOP Web Development
Thanks for the tips that you give it's very useful!
genzoeri
Don't forget to secure your site from http attack and html injection. Also don't forget to contact your administrator server to make sure that all of the site is secure from the server.
roboguyspacedude
I like this article, it gives good advice and helped me understand how to make my php more secure.
bukaida
@izcool
Quote:
I didn't mention that before, but Image Verification is one of the best options people should use if you are making a registration form of some sort.


No dear, nothing is fully secured.The image verification technique before entering data can also be cracked with advanced level OCR algorithms(for degraded images) and a bit of AI programming.The war between cracker and system security manager is a never ending thing. Very Happy
powers1983
bukaida wrote:
@izcool
Quote:
I didn't mention that before, but Image Verification is one of the best options people should use if you are making a registration form of some sort.


No dear, nothing is fully secured.The image verification technique before entering data can also be cracked with advanced level OCR algorithms(for degraded images) and a bit of AI programming.The war between cracker and system security manager is a never ending thing. Very Happy


What about a garbled image that asks a question? Like it spells out a numerical problem (eg. four plus seven).

Or maybe asks for the capital of a well known country or some other general knowledge that most people with access to the internet will know.

But vary it so any code that can read the actual text of the image still has to process the text and if it is sufficiently badly written (yet understandable by a person). (eg. wots sicks teen ad numb brr of cont 1n 3nt5 = 22).
Mosquito.Tyler
powers1983 wrote:
(eg. wots sicks teen ad numb brr of cont 1n 3nt5 = 22).


Problem with that is, any person who doesn't spend much time in online games wouldn't understand that.

I suppose an image with a question on it would be better than an image with the answer. For the registration on my forum I have a VIP code addition. The code itself is written on a separate page inside a paragraph, but it is easily found by human eyes. I don't know how effective it is, but I've never had any issues with bots or anything.

As for bots reading image messages, wouldn't splitting the image into 2 or more separate images prevent it?
icedrakon
I am not pro on web design but i try to be on security try one om the books that i have on my webpage it is called php security pro...

I know you will find it useful to secure your site..

Best regards .....
Fire Boar
I reckon that the best sort of security is neither base64, nor MD5. Base64 can be decoded so easily it's obscene, whereas MD5 offers no way to recover the information (it's great for passwords where you only need to compare the data, but for other things like cookies that you'll want to read - completely useless).

I suggest something like this:

1) You have a "sitewide key" which is a random string of characters.
2) For each individual encryption, you generate a random key using the following code, or something similar:

Code:
$key = md5(rand(1, 100)*microtime());


This is stored on the database in a table which may or may not be called "sessions"; with the IP of the user stored too.

3) You invent a way to combine the sitewide key, the individual key and the string of data you want to encode.
4) You set the encoded string as a cookie.


This is great because you can restrict the cookies to only a single IP and the cookie is completely different every time a new session starts so it is impossible to replicate and steal a cookie.
Ryuujin
Great post.
But, I have one question/complaint...
"8 - Never Use Sessions ! "
I think you can still do this if you do it right.
I was told a method I think will work.
Basically when they login, record the IP. Then on EVERY page check if its the same IP. That way it should stop Session hi-jacking.

What do you think about this?
Or is my thinking faulty?
adrenaline_rush
Wow! That was extremely confusing. Ive really only glanced at php coding before and never really learnt it. So, yea, that really was intense to try and understand. Can anyone suggest any good sites to learn php?
DoctorBeaver
You kids make me feel really ancient. Sad

I started programming in 1979 on what was then a state-of-the-art machine - IBM 360. I was also, at that time, messing around with a Commodore PET. I then moved to a Data General Nova on which we had to key in the bootstrap routine using toggle switches for the address & instruction. Oh deep joy!

I couldn't list all the languages I've used because, as someone else said, I'd use a language for a particular project then never use it again (LISP, ADA and Turbo Pascal spring to mind).

The main languages I've used are IBM BAL, COBOL, BASIC, Pascal, Fortran, 808x asm, 6800/68000 asm, 6502 asm, K-man, C, C++, and now php. Incidentally, I find php among the easiest.

I think that once you know the techniques behind programming it doesn't really matter what language you use.

But, to the point at hand - I agree that some fuller descriptions of the potential problems & why particular solutions are preferable to others would have been useful. To be honest, the most useful thing for me in this thread has been the link to SafeSQL. Why oh why haven't I heard of that before! Mad

I use sessions as well as cookies. I set up some session variables that I'll need in a lot of places and check cookie data at the top of each page (I do all that in an include file so if I change it once, the change is reflected everywhere)
programador
thank you so much. it helps a lot.
andyd34
With regards to sql injection and user submitted data I tend to verify the data I tend to verify it with a regex.

Code:

if($_POST['field'] && !ereg('[0-9][a-zA-Z]', $_POST['field']) {
echo 'Invalid input'; exit; }


another way try to secure things id

Code:

foreach($_POST as $string) {
$string = addslashes($string);
$string = htmlentities($string);
}


I am resonably new to PHP and would appreciate any comments
rvec
unstickied it, now -closed- . Going to make a new security and PHP FAQ sticky later. This one is a bit outdated.
Related topics
How to get your dynamic PHP website crawled better by se ?
How to create a dynamic PHP website.
Secure website with password?
Simple login system
installing apache,mysql and php on windows
full PHP website? help need please
Can someone Make Ma A Website plz? (renamed)
Buying Website - 1000+ FRIH$
SEO/ publish my php website
PHP Wordcut
Php Begginer
For PHP & MySql newbies
Need a Contact form from HTML/PHP
PHP website with SQL Database.
This topic is locked: you cannot edit posts or make replies.    Frihost Forum Index -> Scripting -> Php and MySQL

FRIHOST HOME | FAQ | TOS | ABOUT US | CONTACT US | SITE MAP
© 2005-2011 Frihost, forums powered by phpBB.