tavsiyem bunlarla uğraşmak yerine prepared statement kullanın.

aşağıdaki kodu kullanıyorum, dw içindeki default fonksiyon. <? f (! function_exists { function GetSQLValueString { if (PHP_VERSION < 6) $theValue = function_exists ? mysql_real_escape_string : mysql_escape_string ; switch return $theValue; } } ?> gencbeyin tarafından 19/Ağu/12 13:41 tarihinde düzenlenmiştir

Güzel dküman ellerine sağlık.

makale için teşekkürler faydalı bi bilgi programcı arkadaslarımız için

SQL Injection Nedir? SQL Injection kısaca veritabanı işlemlerinizde sorgularınızın başka kişiler tarafından zararlı hale getirildiği işlemdir. Bu sorun genellikle kullanıcıdan gelen bilgilerin kontrol edilmeden, filtrelenmeden işleme konulması ile ortaya çıksada basit bir unutkanlık bile buna yol açabilir. SQL Injection sistemleriniz için oldukça tehlikelidir. Kullanılan ynteme gre kimi zaman veritabanınızın boşaltılması, kimi zamanda veritabanınızın bir yedeğini bir başkasının eline geçmesini sağlayabilir. Hatta içerik ynetim sistemine sahip bir sisteme sahipseniz ynetici hesabınızın başkasının eline geçmesi sonucu sisteminize geriye dnüşü olmayan hasarlar verilmesini sağlayabilir. Bu makalede SQL Injection hakkında dikkat edilmesi gereken temel başlıklardan sz edeceğim. Tarayıcı Tarafında Dikkat Edilmesi Gerekenler Dikkat edilmesi gereken 2 ana başlık var. Web sayfası tarafında dikkat edilmesi gerekenler ve sayfa işlenirken dikkat edilmesi gerekenler. Bu başlıkta web sayfasında, yani veri daha işleme konulmadan dikkat edilmesi gerekenlerden bahsedeceğim. Sayfalarımızda temel girdi çıktı işlemlerini formlar veya form elemanları aracılığı ile gerçekleştiriyoruz. Mesela basit bir form düşünelim. Formda basit alanlarımız olsun. Kullanıcı adı ve şifre girilmesini istediniz. Siz bu alanlara yalnızca belirli sayıda karakterlerin girilmesini istiyorsunuz. Html tagleri ile limitlerinizi tanımladınız. Artık kullanıcı adı ve şifre blümlerine rneğin 10 karakter girilmesini sağlıyorsunuz. Ama baktınız bu yetmiyor. Kullanıcı adına yalnızca alfanumerik karakterler girilsin dediniz. Js -javascript- ile bunu da gerçekleştirdiniz. Artık formunuz gayet düzgün bir şekilde, istediğiniz gibi işliyor... Byle düşünüp işinize devam ederseniz yanılırsınız. Bu tanımlamalara hiçbir zaman güvenmemeniz gerekiyor. Kullanıcı sayfasının üzerinde firebug ve benzeri programlar aracılığı ile her türlü manipülasyon işlemleri yapılabiliyor. Siz 10 karakter sınırı koyarsınız, kullanıcı bunu alır 20 yapar. Siz buna güvenip sayfanız işlenirken herhangi başka bir sorgu eklemezseniz kullanıcı rahatlıkla 20 karakterli bilgisini veritabanına kaydetmeyi başarır. Js ile sadece harf girilmesini sağladığınızı düşündünüz. Kullanıcı tarayıcısındaki js desteğini kapattığı an tüm sorgunuz de-aktif hale gelir. Bunlar bu rnekte basit gibi grünsede bir çok kişi bu hatayı yapıp daha sonrasında formu işlerken herhangi bir kontrol yapmadan geçiştiriyor. Bu da takdir edersiniz ki çok büyük bir güvenlik açığına sebep oluyor. Ayrıca sayfalarınıza başka bir dil veya sayfa aracılığıyla da bilgi gnderilebilir. Alan adları uygun şekilde ayarlandıktan sonra bir başkası kendi hazırladığı sayfayı sizin sayfanızdan geliyormuş gibi gnderebilir ve çalışmasını sağlayabilir. Sunucu tarafında gerekli nlemleri almayıp sayfanızdaki nlemlere güvendiğinizde yine çok büyük bir kapıyı hırsızlar için açık bırakmış oluyorsunuz. Sayfa İşlenirken Dikkat Edilmesi Gerekenler Yukarıda sayfamızı hazırlarken dikkat etmemiz gerekenleri grmüştük. Şimdi bu sayfayı sunucu tarafında işlerken dikkat etmemiz gerekenlerden bahsedelim. Üstteki rnekten devam edelim. Formumuz yine kullanıcı adı ve şifre alanlarını içersin. Kullanıcı adı ve parola alanlarına max. 10 karakter girilmesini ve kullanıcı adında yalnızca alfanumerik karakterlerin girilmesini isteyelim. Bunu sunucu tarafında nasıl sorgulayabiliriz diyebilirsiniz. PHP'nin yerleşik kütüphanesinde bu işlemler için bir dizi komut tanımlıdır. Bunlardan isteğinize uygun olanları kullanabilirsiniz. Ayrıca bu komutlar sizin için yetersizse regular expression kullanarak ve tanımlayarak istediğiniz kontrolün yapılmasını sağlayabilirsiniz. PHP'nin içindeki bazı komutları ve ne işe yaradıklarından bahsedelim. Altta gsterdiğimiz komutları kullanabilmeniz için php versiyonunuzun en az 4.0.4 olması gerekmektedir. Ayrıca fonksiyonlar geriye dnüş değeri olarak true/false dndürür. ctype_alnum : Girdinin tüm karakterlerinin alfanumerik karakterlerden oluşup oluşmadığını sorgular. Alfanumerik; a-z arası alfabe karakterleri ve 0-9 arası rakamları kapsar. http://php.net/manual/tr/function. ctype-alnum. php ctype_alpha : Girdinin tüm karakterlerinin alfabetik karakterlerden oluşup oluşmadığını sorgular. Alfabetik karakterlerin içerisinde Türkçe karakterler yer almaz. Türkçe karakterlerle ilgili sorgunun nasıl yapılacağını altta ayrıca gstereceğim. www.php.net/manual/tr/function. ctype-alpha. php ctype_lower : Girdinin tüm karakterlerinin küçük harflerden oluşup oluşmadığını sorgular. ctype_upper tam tersi, büyük harfleri sorgular. http://www.php.net/manual/tr/function. ctype-lower. php http://www.php.net/manual/tr/function. ctype-upper. php Ctype komutları dışında işinize yarayabilecek diğer fonksiyonlar şyledir. is_float : Girdinin float/double tipinde (10.2 gibi) olup olmadığını sorgular. http://se2.php. net/manual/tr/function. is-float. php is_bool : Girdinin mantıksal true/false tipinde olup olmadığını sorgular. 1/0 gibi değerler false dner. http://se2.php. net/manual/tr/function. is-bool. php empty : Girdinin boş olup olmadığını sorgular. Aşağıdaki karakterler boşluk olarak ele alınır; 1 0 (bir tamsayı olarak 0) 2 "" 3 "0" (bir string olarak 0) 4 NULL 5 FALSE 6 array 7 var $var; http://se2.php. net/manual/tr/function. empty. php is_int : Girdinin tamsayı olup olmadığını sorgular. http://se2.php. net/manual/tr/function. is-int. php is_numeric : Girdinin sayısal bir tür olup olmadığını sorgular. Bilimsel gsterimler (1e5), tamsayılar ve noktalı sayıları kapsar. http://se2.php. net/manual/tr/function. is-numeric. php isset : Girdide belirtilen değişkenin tanımlı olup olmadığını sorgular. Değişken null değer içeriyorsa da false dndürür. http://se2.php. net/manual/tr/function. isset. php strlen : Girdinin karakter sayısı uzunluğunu dndürür. http://php.net/manual/en/function. strlen. php Yerleşik, işinize yarayabilecek komutlar ve ne işe yaradıklarından bahsettik. Üstte alpha ve alnum komutlarının Türkçe karakterlerini sorgulamadığını sylemiştim. Şimdi onları nasıl kontrol edebileceğinizden ve birkaç farklı sorgudan bahsedelim. Eğer girdinin içerisinde Türkçe karakter geçip geçmediğini sorgulamak isterseniz; 1 if(preg_match 2 echo "Türkçe karakter içeriyor"; Eğer girdinin yalnızca Türkçe karakterleri içerecek şekilde alfabetik karakterlerden oluşup oluşmadığını sorgulamak isterseniz; 1 if(preg_match 2 echo "Alfabetik karakterlerden oluşuyor"; Üstteki işlevin alfanumerik için olanı; 1 if(preg_match("/^ +$/iu","kontrol edilecek girdi")) 2 echo "Alfanumerik karakterlerden oluşuyor"; Bu fonksiyonlar neredeyse tüm form işlemlerinize yetecek, güvenilir fonksiyonlardır. Gelen verinin hangi tipte ve nasıl olmasını istiyorsanız bunlardan uygun olanlar ile sınamamız gerekiyor. Verilerin Filtrelenmesi Script tarafında yapmamız gereken ikinci işlem verilerimizi filtreleme işlemi olmalıdır. Bir üst maddede verilerimizin tiplerini ve biçimlerini sorgulamayı ğrenmiştik. Bu aşamada ise verilerimizi kullanırken yani veritabanı ile iletişime girerken yapmamız gerekenlerden bahsedeceğim. Bu iki madde aslında birbirlerini tamamlayan maddelerdir. İkisinden birisini atlamanız halinde bir açık kapı bırakmış olursunuz. Benim size nerim bu iki maddedeki kurallara uyup o şekilde yolunuza devam etmeniz olur. Başkaları sizin sisteminize sızmak için sizin yaptığınız hataları, bıraktığınız arka kapıları ararlar. Eğer tembellik edip, bunu da bırakırsam bir şey olmaz bulamazlar şeklinde düşünürseniz ileride olası bir durumun tohumlarını ekmişsiniz demektir. Filtreleme aşamalarını maddeleyecek olursak; 1. Kullanıcıya hiçbir zaman güvenmeyin.. En ufak ihtimali dahi gzden kaçırmadan dikkatli bir şekilde yolumuza devam etmemiz gerekiyor. En büyük düşmanımız kullanıcılarımızdır. 2. Veritabanındaki metinsel alanlara girdi yaparken girdileri tek tırnakların arasına alın. 1 insert into test values 3. Sorgulardaki db ismi, tablo adı, kolon adları, takma isimler gibi tanımlayıcılarda yatık tırnak kullanın. 1 select `isim`, count as `toplam` from `tablomuz` ... 4. Tüm girdilere kaçış işlemi uygulayın. Bu işlem girdinizdeki veritabanına tehdit oluşturabilecek karakterlerin nlenip zararsız hale getirilmesini sağlar. Mysql veritabanı için: mysql_real_escape_string 5. Sorgularda zel anlamı bulunan % ve _ karakterlerine ayrıca escape işlemi uygulayın. addcslashes komutu 2. parametrede belirtilen karakterlere escape işlemi uygulayan yararlı bir komuttur. 1 $girdi=addcslashes 2 select xx from `tablom` where isim like '$girdi%' 6. Veritabanındaki sayısal alanlara girdi yaparken verinin belirttiğiniz türde olduğundan emin olmak için intval tarzı komutları kullanın. intval belirtilen girdiyi tam sayıya çevirir. Float türü için floatval komutunu kulanabilirsiniz. 7. Sorgumuzda "order by girdi" şeklinde bir ifade kullanırken girdide belirtilen alan adının tablodaki alanlardan bir tanesi olup olmadığını sorgulayın. 1 $res=mysql_query ; 2 while($row=mysql_fetch_row 3 $tabloAlanlari =$row ; 4 if(! in_array 5 $girdi="belirleyeceğinizDefaultKolonAdı"; 8. Veritabanınızdan sadece sayfanızda kullanacağınız kadar bilgiyi alın. 9. SQL'e ait bazı zel kavramları ASCII karşılıklarıyla, emsalleriyle güncelleyin. 01 $girdi=str_ireplace("where","&#119here",$girdi); 02 $girdi=str_ireplace("drop","&#100rop",$girdi); 03 $girdi=str_ireplace("select","&#115elect",$girdi); 04 $girdi=str_ireplace("union","&#117nion",$girdi); 05 $girdi=str_ireplace("like","&#108ike",$girdi); 06 $girdi=str_ireplace("update","&#117pdate",$girdi); 07 $girdi=str_ireplace("delete","&#100elete",$girdi); 08 $girdi=str_ireplace("insert","&#105nsert",$girdi); 09 $girdi=str_ireplace("show","&#115how",$girdi); 10 $girdi=str_ireplace("alter","&#97lter",$girdi); Bunlar düz kullanımlarda geçerli olan kurallardır. Birde PHP'nin içerisinde yerleşik olarak bulunan PDO dediğimiz hazır veritabanı yapıları mevcuttur. Bunları kullanarak zahmetsiz, seri ve güvenilir bir şekilde sorgularınızı hazırlayabilirsiniz. PDO'yu kullanabilmek için PHP versiyonunuzun en az 5 olması gerekmektedir. PHP PDO: http://tr. php. net/manual/tr/book. pdo. php zetle benim syleyeceklerim bu kadar. Bu kurallara dikkat ettiğiniz müddetçe, veritabanınızın güvenliğini de gerekli şekilde sağladınız müddetçe pek problem yaşamayacağınızı düşünüyorum. Eksiklerim, atladığım noktalar elbette olabilir. Bunlara dikkat ettiğiniz halde yine sorunlar yaşayabilirsiniz. Bunlar sizin kodlamalarınıza, davranışlarınıza, güvenlik bilginize gre ortaya çıkabilir. Sisteminizin sorunsuz olmasını istiyorsanız mutlaka bilgili bir veya birkaç kişiye sisteminizi test ettirin. Hatta imkanınız varsa sisteminizi kullanıcı testlerine sokun. En iyi sorun bulma yntemi bu şekildedir. Ne kadar çok kişi sisteminizi test ederse o kadar sorunsuz bir sisteme sahip olursunuz.

eline sağlık hocam. Programming is our Religion, Algorithms are Our Bible & We./make Our Own GOD

aşağıdaki kodu kullanıyorum, dw içindeki default fonksiyon. <? f (! function_exists { function GetSQLValueString { if (PHP_VERSION < 6) $theValue = function_exists ? mysql_real_escape_string : mysql_escape_string ; switch return $theValue; } } ?> Keşke bunun gibi tek bir fonksiyon hazırlayabilsekte sorunlarımız kalmasa ama yetmiyor :) Üstte nedenlerini açıkladım. Sadece bunu kullanırsanız yine açık kapınız kalıyor.

emeğine sağlık İnsanları sevin, saygınızı gsterin ama kesinlikle insanlara acımayın. Çünkü acıdığınız anda acınacak duruma düşüyorsunuz