Treci peste conţinut
Prima pagină ‹ PHP General ‹ Cod PHP ‹ Secure login
Ai o întrebare legată de PHP? Incercăm să îi găsim soluţie. Sau poate doar vrei să publici un cod interesant.
Sâm Feb 04, 2012 2:53 pm
Lucrez la un panou de administrare, momentan am facut doar sistemul de login si as dori sa va intreb ce masuri de securitate trebuie sa mai iau, ce trebuie imbunatatit, adaugat sau lasat asa.
login.php
<?php
require_once('resources/includes/settings.inc.php'); require_once('resources/includes/security.inc.php'); if(isset($_POST['member_login'])) { $omusername = secureString('mres', $_POST['member_username']); $ompassword = secureString('mres_md5', $_POST['member_password']); $login = mysql_query("SELECT omid, omusername, ompassword, omsalt FROM office_members WHERE omusername='$omusername'"); if(mysql_num_rows($login)==1) { while($dlogin = mysql_fetch_array($login, MYSQL_ASSOC)) { $ompassword1 = md5($ompassword . $dlogin['omsalt']); $ompassword2 = $dlogin['ompassword']; if($ompassword1==$ompassword2) { session_start(); validateMember($dlogin['omid'], $dlogin['omusername']); header('Location: index.php'); } } } else { echo mysql_error(); } } ?> <form action="login.php" method="post" name="members_login" id="members_login"> <ul> <li>Utilizator</li> <li><input type="text" name="member_username" id="member_username" value=""></li> <li>Parola</li> <li><input type="password" name="member_password" id="member_password" value=""></li> <li> </li> <li><input type="submit" name="member_login" id="member_login" value="Login member"></li> </ul> </form>
security.inc.php<?php
function generateSalt($param='') { $var = md5(uniqid() . substr(md5(rand(0, 1000000) . time()), 0, 35) . '!@#$%^&*()_+{}:"|<>?-=[]'); return $var; } function secureString($param1='', $param2='') { if($param1=='mres') { $param2 = mysql_real_escape_string($param2); } elseif($param1=='mres_md5') { $param2 = mysql_real_escape_string(md5($param2)); } return $param2; } // Checks if member is authenticated function authenticatedMember($param='') { if(isset($_SESSION['authenticated']) && $_SESSION['authenticated']) { return true; } else { return false; } } function unauthenticatedMember($param='') { header('Location: login.php'); } function deauthenticateMember($param='') { $_SESSION = array(); session_destroy(); header('Location: login.php'); } function validateMember($param1='', $param2='') { session_regenerate_id(); $_SESSION['authenticated'] = 'rogerthat'; $_SESSION['idMember'] = $param1; $_SESSION['userMember'] = $param2; } ?>
index.php<?php
require_once('resources/includes/settings.inc.php'); require_once('resources/includes/security.inc.php'); session_start(); if(authenticatedMember()==false) { echo unauthenticatedMember(); die(); } ?> <!DOCTYPE html> <html> ... etc
logout.php<?php
require_once('resources/includes/settings.inc.php'); require_once('resources/includes/security.inc.php'); session_start(); if(authenticatedMember()==false) { echo unauthenticatedMember(); die(); } else { echo deauthenticateMember(); die(); } ?>
Random: Man ... I suck at this game. Can you give me some pointers?
Programmer: 0x3a28213a, 0x6339392c, 0x7363682e
Sâm Feb 04, 2012 3:42 pm
Din ce m-am uitat ai 2,3 chestii ciudate prin cod:
1.
if(mysql_num_rows($login)==1) { while($dlogin = mysql_fetch_array($login, MYSQL_ASSOC)) {
2. function generateSalt($param='') {...} function authenticatedMember($param='') { ... } function unauthenticatedMember($param='') { ... }
3. echo unauthenticatedMember();
Tu ai testat codul asta? Cu ini_set('display_errors',1); error_reporting(E_ALL); ???
Sâm Feb 04, 2012 5:36 pm
Da, l-am testat, no errors. Am folosit functii ca sa fie mai usor de modificat pentru mine, nu stiu daca pentru toata lumea.
Aici n-am inteles ce vrei sa spui. De ce e ciudat?
if(mysql_num_rows($login)==1) { while($dlogin = mysql_fetch_array($login, MYSQL_ASSOC))
Random: Man ... I suck at this game. Can you give me some pointers?
Programmer: 0x3a28213a, 0x6339392c, 0x7363682e
Sâm Feb 04, 2012 9:08 pm
Ok, vad ca nu-ti dai seama ce vreau sa spun, asa ca o sa-ti explic:
1. verifici daca ai doar un rand, si dupa pui un while. While il folosesti atunci cand ai mai multe randuri, cand vrei sa repeti instructiunea de mai multe ori
2. puteai sa observi ca am dat doar anumite functii, care au un argument $param, care mai are si valoarea default '', dar care nu este folosit in corpul functiilor, de ce pui functia asta? Nu prea e bine pentru ca poate lucrezi intr-o echipa si folosesti un IDE mai destept, exemplu Netbeans, care stie sa-ti adauge @param si sa-ti faca autocomplete la functie cand o folosesti. Ceilalti din echipa vor trebui sa-ti verifice codul sa vada ce face $param
/** * Checks if member is authenticated * @param string $param * @return bool */ function authenticatedMember($param='') { // corpul functiei unde nu este folosit $param }
3. echo deauthenticateMember(); die();
function deauthenticateMember($param='') { $_SESSION = array(); session_destroy(); header('Location: login.php'); }
o functie declarata asa, nu este nevoie de echo, pentru ca nu ai output, si ai grija cand folosesti echo inainte de headere, o sa-ti dea eroare "Headers already sent..."
Sâm Feb 04, 2012 10:19 pm
Intradevar, while este un loop si mi-am luat prostul obicei sa o folosesc si la un singur rand, cand as putea sa folosesc fetch_array si fara while.
Parametrul gol pe care il folosesc in functii ($param='') este din cauza setarilor de pe serverul firmei de hosting. Daca fac o functie simpla (eg. function ceva() { /* cod */ } o sa-mi dea o eroare si o sa-mi zica ca nu am setat nici un parametru si imi da o eroare, daca folosesc error_reporting(0); nu mai afiseaza eroarea dar nici nu functioneaza functia.
Pentru greseala cu echo la functie, am folosit mai multe versiuni de AppServ ... iar atunci cand dadeam return la o valoare dintr-o functie, pe unele versiuni imi aparea valoarea din functie doar daca scriam <?php functie(); ?> iar pe alte versiuni imi aparea valoarea doar daca foloseam <?php echo functie(); ?> sau <?= functie(); ?> si am zis sa folosesc echo pentru toate ca sa nu mai fie nici o problema pe nici o versiune. Daca functia nu returneaza nici o valoare e ok sa nu folosesc echo, dar totusi sa am siguranta ca nu se poate intampla nimic rau?
Random: Man ... I suck at this game. Can you give me some pointers?
Programmer: 0x3a28213a, 0x6339392c, 0x7363682e
Sâm Feb 04, 2012 10:30 pm
Cum am modificat pana acum
login.php
<?php
require_once('resources/includes/settings.inc.php'); require_once('resources/includes/security.inc.php'); if(isset($_POST['member_login'])) { $omusername = secureString('mres', $_POST['member_username']); $ompassword = secureString('mres_md5', $_POST['member_password']); $login = mysql_query("SELECT t1.omid, t1.omdid, t1.omusername, t1.ompassword, t1.omsalt, t2.omdid, t2.omdname FROM office_members AS t1 LEFT JOIN office_members_departments AS t2 ON t2.omdid=t1.omdid WHERE t1.omusername='$omusername'"); if(mysql_num_rows($login)==1) { $dlogin = mysql_fetch_array($login, MYSQL_ASSOC); $ompassword1 = md5($ompassword . $dlogin['omsalt']); $ompassword2 = $dlogin['ompassword']; if($ompassword1==$ompassword2) { session_start(); validateMember($dlogin['omid'], $dlogin['omusername'], $dlogin['omdid'], $dlogin['omdname']); header('Location: index.php'); } } else { echo mysql_error(); } } ?> <!DOCTYPE html> <html> <head> <title><?php echo get_settings('website_title'); ?></title> <link rel="stylesheet" type="text/css" media="all" href="resources/styles/default/login.css"> <meta name="robots" content="noindex, nofollow"> </head> <body> <form action="login.php" method="post" name="members_login" id="members_login"> <ul> <li>Utilizator</li> <li><input type="text" name="member_username" id="member_username" value=""></li> <li>Parola</li> <li><input type="password" name="member_password" id="member_password" value=""></li> <li> </li> <li><input type="submit" name="member_login" id="member_login" value="Login member"></li> </ul> </form> </body> </html>
index.php<?php
require_once('resources/includes/settings.inc.php'); require_once('resources/includes/security.inc.php'); require_once('resources/includes/sessions.inc.php'); ?> <!DOCTYPE html> <html> <head> <title><?php echo get_settings('website_title'); ?></title> <link rel="stylesheet" type="text/css" media="all" href="resources/styles/default/default.css"> <meta name="robots" content="noindex, nofollow"> </head> <body>
security.inc.php<?php
function generateSalt() { $var = md5(uniqid() . substr(md5(rand(0, 1000000) . time()), 0, 35) . '!@#$%^&*()_+{}:"|<>?-=[]'); return $var; } function secureString($param1='', $param2='') { if($param1=='mres') { $param2 = mysql_real_escape_string($param2); } elseif($param1=='mres_md5') { $param2 = mysql_real_escape_string(md5($param2)); } return $param2; } // Checks if member is authenticated function authenticatedMember() { if(isset($_SESSION['authenticated']) && $_SESSION['authenticated']) { return true; } else { return false; } } function unauthenticatedMember() { header('Location: login.php'); } function deauthenticateMember() { $_SESSION = array(); session_destroy(); header('Location: login.php'); } function validateMember($param1='', $param2='', $param3='', $param4='') { session_regenerate_id(); $_SESSION['authenticated'] = 'rogerthat'; $_SESSION['idMember'] = $param1; $_SESSION['userMember'] = $param2; $_SESSION['idMemberDepartment'] = $param3; $_SESSION['nameMemberDerpartment'] = $param4; } ?>
sessions.inc.php<?php
session_start(); if(authenticatedMember()==false) { unauthenticatedMember(); die(); } ?>
logout.php<?php
require_once('resources/includes/settings.inc.php'); require_once('resources/includes/security.inc.php'); session_start(); if(authenticatedMember()==false) { unauthenticatedMember(); die(); } else { deauthenticateMember(); die(); } ?>
Question1: am citit pe ici pe colo cum ca require_once si include_once incetinesc mult timpi de incarcare ... imi recomandati altceva?
Question2: die(); am invatat sa-l folosesc din tutoriale care se gaseau in aceleasi conditii. Mai are vreun rost die() daca inainte folosesc header('location');?
Question3: Ma gandesc sa folosesc metodata asta pentru securitatea tuturor formularelor impotriva CSRF attacks. Should fix it? http://net.tutsplus.com/tutorials/php/s ... form-keys/
Ultima oară modificat de Darky pe Sâm Feb 04, 2012 10:42 pm, modificat 1 dată în total.
Random: Man ... I suck at this game. Can you give me some pointers?
Programmer: 0x3a28213a, 0x6339392c, 0x7363682e
Sâm Feb 04, 2012 10:41 pm
AppServ?
Schimba firma de hosting, altfel te vei invata cu niste chestii gresite.
Conteaza la ce tip de date vrei sa faci echo, in mod normal ar trebui sa fie string, sau ceva care poate fi interpretat ca string. Cat despre functiile respective, poate aveai echo in functie, in loc de return si atunci da, la <?php functie()?> o sa-ti afiseze outputul. Si ai grija la short open tags, mai ales daca folosesti xml.
Sâm Feb 04, 2012 10:51 pm
<? ?> <?= ?> m-am invatat sa nu le mai folosesc niciodata, just good'ol <?php ?>
www.appservnetwork.com
e ok cum am modificat?
Random: Man ... I suck at this game. Can you give me some pointers?
Programmer: 0x3a28213a, 0x6339392c, 0x7363682e
Sâm Feb 04, 2012 11:06 pm
Iti recomand sa iei wamp, din ce vad appserv ala nu mai este updatat si foloseste versiuni de php si mysql care nu sunt inca stabile.
Din ce vad la CSRF in tutorialul adaugi un token la form si pare ok...
Ai putea adauga un counter, astfel incat cineva sa nu incerce de 1000000 de ori sa se logheze.
La inregistrare (daca ai), sau cand introduci date de la utilizator in baza de date, trebuie sa ai grija si la XSS, nu doar la SQL injection.
Iti recomand sa folosesti alta functie hash, md5 este depasita de multi ani.
Si tot vei fi vulnerabil la atacuri de tip man in the middle, asta se rezolva cu un certificat...
Dum Feb 05, 2012 1:53 am
pentru XSS ma gandeam sa folosesc htmlspecialchars dar am o problema. pentru continutul unei stiri de exemplu, daca folosesc un text editor, o sa am implicit texte bolduite, headinguri, etc... poti sa-mi dai vreun tutorial ceva? si alta functie inafara de sha nu mai stiu :d xampp nu pot sa-l sufar
daca scot eu doar tag-ul <script>, gen ... crezi ca scap de problema cu xss?
<?php
$html = '<!doctype html> <html> <head> <meta charset="utf-8"> <title> hey </title> <script> alert("hello"); </script> </head> <body> hey </body> </html> ';
$html = preg_replace('#<script(.*?)>(.*?)</script>#is', '', $html);
echo $html;
?>
Random: Man ... I suck at this game. Can you give me some pointers?
Programmer: 0x3a28213a, 0x6339392c, 0x7363682e
Dum Feb 05, 2012 9:24 am
Mesaje: 851 Localitate: Cluj-Napoca
Dum Feb 05, 2012 10:08 am
Eu folosesc in principal framework-uri asa ca iti pot spune sa te uiti in codeigniter, este cel mai simplu, in system/core/Security.php ai si xss clean si csrf.
Si ca sa verifici ai aici mai multe exemple de xss:
http://ha.ckers.org/xss.html
|