الكوكيز – أسرار وحماية

مدرج تحت قسم: دروس
21 يوليو 2006

بالطبع لا يخفى على أي مبرمج صفحات ويب تفاعلية (مواقع ديناميكية) كمبرمجين (asp – php – jsp – asp.net) أهمية الكوكيز، لأنها العنصر الرئيسي في سكربتات الأعضاء والمنتديات.

ونحن نتكلم عنها في php لأنها اللغة التي نبرمج بها، وتعتبر لغة بي اتش بي من أسهل اللغات تعاملا مع الكوكيز، فعند إدخال الكوكيز نستخدم الدالة.

setcookie('name',val,time);

وطبعاً يواجه البعض مشاكل في إدخال الكوكيز كعدم عملها وإرسال أخطاء، فما السبب في ذلك؟

السبب في ذلك هو أنك تكون قد قمت بإرسال أي معلومات قبل إدخال الكوكيز بالدالة print مثلاً، لأن الكوكيز هو عبارة عن header للصفحة وعندما تقوم بإرسال أي header للصفحة يجب أن يكون قبل أوامر الطباعة أو غيرها، وعند استخراج الكوكيز نستخدم المتغير.

$_COOKIE['name'];

بعد أن تكلمنا عن إدخال الكوكيز واستخراجها سنتكلم عن مخاطرها وأسرارها.

فما مخاطر الكوكيز؟

الكوكيز طبعاً هي عبارة عن ملفات تحفظ في جهاز المتصفح للموقع، وطبعاً يجب استخدام أحد المتصفحات لأنها تكون مبرمجة لاستقبال الكوكيز بالشكل الصحيح، ولأنها ملفات يمكن تعديلها، يوجد برامج كثيرة لتعديل الكوكيز مثل Cookie Editor، وأداة التعديل المصاحبة للموزيلا والفايرفوكس. وعندما يكون الكوكيز قيمة واحدة ويتم التحقق منها مباشرة، يمكن استغلالها للدخول بمعلومات المسئولين.

مثال:
إذا كانت قيم الكوكيز الموجودة لدينا.

user id
user password(md5)

وطبعاً لنفترض أن السكربت محمي ولم يقم بمعرفة الباسوورد، وكان أمر التحقق من الكوكيز كالتالي:

$userid=$_COOKIE['userid'];
$userpwd=$_COOKIE['userpwd'];
$query=mysql_query("select * from users where userid=$userid and userpwd=$userpwd");

أليست هذه هي الطريقة التي يقوم الأغلب بالتحقق بها؟
طبعاً هنا على اعتقاد المبرمج أنه لا يمكن استغلالها، ولكن هل هذا صحيح؟

جرب أن تضع قيمة الكوكيز.

1/*

وانظر ماذا حدث هنا! لقد قام بالتحقق من userid فقط وتجاهل الباسوورد باستخدام العلامة /* والتي تنهي الاستعلام.

ثغرة أخرى

ضع كوكيز userpwd بقيمة

1 or 1=1/*

وانظر ماذا حدث هنا! أرأيتم الخطأ البسيط، مالذي قام بعمله؟ لقد حدثت ثغرة خطيرة وهي الدخول حتى بدون كلمة مرور أو اسم مستخدم!

يوجد خطأ آخر شائع لدى المبرمجين، وهو وضع الكوكيز بقيمة واحدة مثل username أو userid، وهذا خطأ لأنه كما رأينا بالأعلى فإنه يمكن التعديل على الكوكيز وهذا سيسهل مهمة المهاجم.

أسرار الأمن في الكوكيز

عند القيام باستخراج الكوكيز يجب التحقق من قيمتها، مثلاً لدينا الـ userid قيمة رقمية، أي أنها لا يمكن أن تكون حرفية. نستخرجها كالتالي:

 $userid=intval($_COOKIE['userid']);

وجرب السابق! أرأيت؟ هنا لا يستطيع استخدام غير الأرقام في الكوكيز. لكن أيضا userpwd غير محمية.

طبعاً إذا كنت لا تريد ان تقوم بعمل دوال للحماية من هذه الثغرات، فما عليك إلا وضع التحقق من الباسوورد بين علامات التنصيص وثم عمل addslashes عند استخراجه:

$userpwd=addslashes($_COOKIE['userpwd']);

وعند كتابة الاستعلام، أفضل طريقة هي أن يكون الاستعلام كالتالي:

$userid=intval($_COOKIE['userid']);
$userpwd=addslashes($_COOKIE['userpwd']);
$query=mysql_query("select * from users where userid='$userid' and userpwd='$userpwd'");

تلميحة: لدينا هنا كعكة ولها قيمتها

setcookie('PHP',$_POST['username']);

التحقق مثل:

if (!empty($PHP)) {
echo 'مرحباً بك في لوحة التحكم !';
}

الكود السابق يتحقق من أن المتغير $PHP ليس فارغاً. ادخله لوحة التحكم. هذا خطأ؟ إذاً ماذا لو طلب هذا الرابط من خلال العنوان كالتالي :

http://localhost/example.php?PHP=Admin

سوف يكون المتغير له قيمة وبالتالي تحقق الشرط السابق فيدخله إلى لوحة التحكم مثلاً.

الذي أريد الوصول له أن نستخدم المصفوفة HTTP_COOKIE_VARS التي تحتوي على قيم الكعكات و يمكننا استخدام المصفوفة _COOKIE اختصاراً للسابقة، إذاً شفرتنا سوف تكون هكذا.

if (!empty($_COOKIE['PHP'])) {
echo 'مرحباً بك في لوحة التحكم !';
}

هنا نفس الكود السابق لكن أضاف عليه مصفوفة $_COOKIE.

لدينا مشكله أخرى، هل هذه الطريقة آمنة بالفعل؟ أعني هل يكفي التحقق إذا كانت الكعكة مسجلة أو بالأصح بها قيمة نعطيها الصلاحية لدخول لوحة التحكم؟
في الحقيقة هناك بعض البرامج التي تستخدم للتلاعب في Headers HTTP و قد تستغل هذه البرامج مع مثل هذه الطرق من التحقق، لذا يجب علينا تخزين اسم المستخدم وكلمة المرور أولاً بهذه الطريقة:

setcookie('PHP_username',$_POST['username']);
setcookie('PHP_password',$_POST['username']);

الآن نتحقق بالطريقة الصحيحة و الآمنة، حيث نقوم بتمرير محتوى الكعكات على استعلام و ننظر إلى النتائج كالتالي:

$per = 0; //لا يوجد صلاحيات، قيمه افتراضية لكي لا نسبب ثغرة أمنية
//الاستعلام
$query = mysql_query("SELECT * FROM user WHERE username='" . $_COOKIE['PHP_username'] . "' AND password='" . $_COOKIE['PHP_password'] . "'");
// التأكد من عدد الحقول
$num = mysql_num_rows($query);// إذا كانت عدد الحقول اكبر من الصفر
if ($num > 0) {
$per = 1; // أعطه الصلاحية
}
// و إلا
else {
$per = 0; // لا تعطه الصلاحية
}

أريد أن انوه أن هذا الاستعلام كتب على فرض أن Magic Quotes في حالة التشغيل الذي سوف نقوم بعمله هو التحقق من قيمة المتغير $per كالتالي:

//لديه الصلاحية
if ($per == 1) {
echo 'مرحباً بك في لوحة التحكم'; // يمكنه الدخول
}
// لا يوجد صلاحية
else {
die('المعذرة لا يمكنك الدخول'); // لا يمكنه الدخول
}

للكاتب Mr.php-ar

  • Share/Bookmark

التعقيبات

  1. غير معروف

التعليقات (12) على ”الكوكيز – أسرار وحماية“

  1. Mr-Fahad

    بارك الله فيك اخي mr.php-ar

    استفدت كثيراً من هذه المقالة ..

    Mr-Fahad

  2. العفو اخي Mr-Fahad ، وبارك الله فيك

    تحياتي

  3. المضياني

    مشكور أخوي أستفدت كثيراً من هذه المقالة

  4. مقاله جميله جداً واستفدت منها حقاً

    رائع اخى الحبيب .. الى الامام :)

  5. بارك الله فيك شرح وافي ومعلومات قيمة

  6. اقف وقفة إعجاب أمام علمكم ” ما شاء الله تبارك الرحمن ”
    بصراحة من أفضل المواضيع المتحدثة عن الكوكيز

    دمت بعلم يارب

    ^ ^

  7. في الحقيقة هذه المعلومات رائعة لكنني أواجه مشكلة مع الكوكيز حيث أنني لم أستطع تشغيل حساب بريدي الإلكتروني وكلما حاولت ذالك طلب مني أن الكوكيز لم يسمح بذلك وأنا لدي متصفح انترنات اكسبلورر7 بالعربية ولا توجد في إعدادات الأمان كلمة كوكيز لذلك أرجو المساعدة

  8. شكرا لك اخى الكريم على المقال الرائع.
    وكا اضافة لأنواع حماية المتغيرات
    هناك الدالة mysql_real_escape_string
    هذه الدالة معروفة انها من اقوى ماتم التوصل اليه لحماية المتغيرات التى يتم ادخالها او استخراجها من قاعدة البيانات
    اكرر شكرى لك على الموضوع اخى الكريم.

  9. شكرا لك اخى الكريم

  10. السلام عليكم ورحمة الله وبركاته

    بارك الله فيك أخي ،، بالفعـل درس روعـة ،، إستفدت منه كثيرا

    جزاك الله خيرا

  11. مشكور على المعلومات القيمة

  12. بارك الله فيك …

أضف تعليقك




يمكنك استخدام الوسوم التالية في التعليق: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>


* حقول مطلوبة