حفره امنیتی تزریق ایمیل در فرمهای تماس با ما

این حفره ای هست که در بعضی از فرمهای «تماس با ما» که اطلاعات وارد شده رو به ایمیل مدیر سایت ارسال میکنن ممکنه وجود داشته باشه.
با این حفره میشه از طریق سایتی که این حفره رو داره، به هر آدرس دلخواه ایمیل ارسال کرد؛ حتی همراه با فایلهای ضمیمه!

اسم این آسیب پذیری/حفره Email injection هست که البته ممکنه بعضیا Email header injection هم بگن.

یک مورد از کدهای «تماس با ما» رو در فروم برنامه نویس گذاشته بودن که این حفره رو داشت. بنده همون کدها رو براتون میذارم که بعنوان نمونه بررسی کنید: دانلود

این آسیب پذیری در فایل send.php وجود دارد.

برای تست کردن این کارها رو انجام بدید:

فیلد email در فایل index.html رو به textarea تغییر بدید.
یعنی به این شکل:

<textarea id="email" name="email" type="email"></textarea>

البته این کار فقط برای تست راحت خودمونه. هکر نیازی نداره که شما این کار رو انجام داده باشید.

خب بعد در فیلد ایمیل، هکر مثلا این رو ارسال میکنه:

sender@anonymous.www>
Cc:someone@example.com

دقت کنید که خطوط خالی آخرش هم لازمن (شما در کادر مربوطه دو صه تا اینتر بزنید).
فرم رو که سابمیت کنید علاوه بر آدرس ایمیل مدیر سایت که در متغییر recipient در فایل send.php تعیین شده، یک ایمیل هم به آدرس مورد نظر هکر (someone@example.com) ارسال میشه.

این تستی رو که گفتم خودم روی هاست و ایمیل های واقعی انجام دادم.

خب این کار از کجا ممکن میشه؟
از اونجایی که مقدار فیلد ایمیل (ایمیل کاربر) مستقیما در پارامتر mailheader درج شده، میشه از این سوء استفاده کرد و کاری کرد که مثلا ایمیلهایی به آدرسهای دیگری هم ارسال بشن از طریق سایت شما.
حالا دیگه جزییات و توضیح طرز کارش مربوط به فرمت درونی پیامهای ایمیل میشه که باید جزییات فنی و طرز کارش رو بدونید.

و اما راه حل چیست؟

خوشبختانه راه حلش ساده است.
باید کاراکترهای ‎r و ‎n رو شناسایی و حذف کنید. چون این کاراکترها در بخش هدرهای ایمیل معنا و کاربرد خاصی دارن.
البته این کار فقط برای فیلدهایی که در پارامتر هدر تابع میل وارد میکنید لازمه، نه برای بقیهء فیلدها.

حالا کد اصلاح شده رو دانلود کنید: دانلود

اگر send.php رو نگاه کنید فقط این کدها بهش اضافه شدن:

$name=str_replace(array("\r", "\n"), '', $name);
$email=str_replace(array("\r", "\n"), '', $email);

دقت کنید که ما میتونستیم این حمله رو از طریق فیلد name هم انجام بدیم، چون این فیلد هم مستقیما در پارامتر هدر تابع mail درج شده بود.
یعنی مثلا حتی اگر در سمت سرور فرمت ایمیل وارد شده توسط کاربر چک میشد و بنابراین ما نمیتونستیم از طریق فیلد ایمیل این حمله رو صورت بدیم، میتونستیم از فیلد name بجاش استفاده کنیم.

5 دیدگاه در “حفره امنیتی تزریق ایمیل در فرمهای تماس با ما

  1. سلام خدمت حمیدرضای عزیز.
    واقعا عالی بود. من که اصلا به این نکته توجه نکردم تا الان!
    البته کار من هک نیست…
    در هر صورت واقعا ممنونم از راهنماییت!

  2. سلام برای تامین امنیت و تست امنیتی سایتم میتونم رو شما حساب کنم البته با هزینه ؟

    لطفا با ایدی ruhyshujy در ارتباط باشید با تشکر

  3. هیچ کس ایمیل وارد شده رو بدون استفاده از توابع فیلتر یا regexp به کار نمی بره، که عملا امکان چنین تزریقی رو غیر ممکن می کنه.

    • هیچکس؟
      دوست عزیز نت پر است از فرمهای تماس با ما که چکهای کافی انجام نمیدن. نمونه کد آماده و مثال توی نت زیاد هست که خیلی های دیگر هم همونطور ور میدارن و استفاده میکنن. چند نمونش رو خودم تاحالا در فرومهای برنامه نویسی دیدم که افرادی درست/معرفی کرده بودن (و طبیعتا دیگران هم ممکنه ازشون استفاده کنن) یا مبتدی ها از جایی کپی کرده بودن. اصلا این مقاله رو بخاطر همین نوشتم چون دیدم فرمهای تماس با ما آسیب پذیر زیاد هستن و افراد همینطور دارن معرفی/کپی میکنن.
      مثالی (فایل دانلودی نمونه) که براتون گذاشتم یکی از همین موارده که در فروم برنامه نویس معرفی شد. هیچ چکی هم انجام نمیده. چند مورد دیگر غیر از این هم دیده بودم که افراد همینطور معرفی و استفاده میکردن.
      نظر به اینکه اطلاعات وارد شده در فرم تماس با ما معمولا در دیتابیس وارد نمیشن و به خود سایت/برنامه و سرور مستقیما ارتباطی ندارن و فقط بعنوان پارامترهای تابع mail درج میشن، خیلی ها ممکنه اونا رو (خوب) ولیدیت نکنن. بعضیا هم ممکنه فقط ولیدیت سمت کلاینت بذارن و سمت سرور چکی انجام ندن، که به این شکل یک هکر میتونه مکانیزم ولیدیت رو براحتی دور بزنه.
      در ضمن این حمله از طریق فیلدهای دیگر هم (مثل فیلد نام) به شرطی که این فیلدها رو در پارامتر هدر تابع mail وارد کنید امکانپذیره (دقیقا مثل فایل نمونه). ممکنه بعضیا ایمیل رو چک کنن ولی اسم رو چک نکنن.
      ضمنا هر regexp ای هم جلوی این حمله رو نمیگیره. regexp اش باید دقیق باشه که اجازهء درج اون کاراکترهای خاص رو در ایمیل نده. بعضیا ممکنه regexp های ناامن طراحی کنن یا بازم همینطور یه چیزی رو از جایی کپی کرده باشن.

  4. سلام

    منم به شخصه تو فرم هایی که مینویسم آدرس Email از 100تا فیلتر رد میکنم تا ازش استفاده کنم، ولی شما خودتون چقدر به تابع filter_var برای اعتبار سنجی ایمیل با FILTER_VALIDATE_EMAIL اعتماد دارید؟!

پاسخ دهید

نشانی ایمیل شما منتشر نخواهد شد. بخش‌های موردنیاز علامت‌گذاری شده‌اند *

*

شما می‌توانید از این دستورات HTML استفاده کنید: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>