درگاههای شبکه خصوصی مجازی (VPN) مستقر بر بستر اینترنت عمومی همواره با جریان پیوستهای از ترافیک تاییدنشده روبهرو هستند. در شرایط عادی، تونلهای رمزنگاری از طریق دستتکانی مبتنی بر کلید عمومی هویت همتایان را تایید میکنند. با این حال، در طول حملات محرومسازی از سرویس توزیعشده (DDoS)، مهاجمان از عدم تقارن محاسباتی سوءاستفاده میکنند: فرستادن میلیونها بسته آغازین ساختگی پروتکل UDP پهنای باند اندکی از مهاجم مصرف میکند، اما سرور دریافتکننده را وادار به محاسبات رمزنگاری پرهزینه و تخصیص حافظه وضعیت نشست در هسته سیستمعامل میسازد.
معماریهای سنتی مانند OpenVPN و IPsec IKEv2 در برابر این تهدید با چالشهای جدی مواجه میشوند. آنها بلافاصله پس از دریافت نخستین بسته کاوشگر، ساختارهای کنترلی انتقال یا بافرهای ارتباط امنیتی (SA) تخصیص میدهند که این امر صفهای حافظه را دچار فرسودگی و سرریز میکند. وایرگارد این بردار حمله را ریشهکن کرده است. این پروتکل با تحمیل اصل بدون حالت بودن (Stateless) تا پیش از تکمیل دستتکانی، و به کارگیری احراز هویت دومرحلهای کد اصالتسنجی پیام (mac1 و mac2) متکی بر کوکیهای گردشی، منابع سرور را در برابر اشباع محافظت مینماید.
در لایه هسته لینوکس، پیادهسازی این پدافند هوشمند در پرونده drivers/net/wireguard/cookie.c قرار دارد. تحلیل معماری رمزنگاری این بخش نشان میدهد که چگونه تونلهای پرسرعت بدون واگذاری منابع به فرستندگان ناشناس، پایداری فراگیر خود را حفظ میکنند.
چالش دستتکانی نامتقارن و انعطافپذیری بدون حالت
الگوی نویز IK که در وایرگارد به کار گرفته شده نیازمند احراز هویت متقابل با ضرب اسکالر بر روی منحنی بیضوی Curve25519 (معروف به X25519) است. ضرب نقطه بر روی منحنی بیضوی در مقایسه با مسیریابی معمولی بسته، نیازمند چرخههای پردازشی بسیار زیادی در واحد پردازش مرکزی (CPU) است. اگر سرور بدون هیچ مانعی هر بسته ورودی نوع یک (Type 1: Handshake Initiation) را پذیرفته و بیدرنگ کلید مشترک را محاسبه میکرد، یک حمله سیلآسا با جعل آدرس مبدا میتوانست تمام هستههای پردازنده را به انحصار خود درآورده و کاربران مجاز را از دستیابی به سرویس بازدارد.
وایرگارد با تفکیک اعتبارسنجی بستهها به دو لایه مستقل، این آسیبپذیری را خنثی ساخته است:
[ دریافت بسته آغاز دستتکانی ]
│
▼
بررسی MAC1 (کلید ایستا)
├─ نامعتبر ──► حذف بیصدا (Zero Response)
└─ معتبر
│
▼
آیا سرور زیر بار سنگین است؟ (ratelimiter.c)
├─ خیر ──► اجرای ضرب اسکالر Curve25519
└─ بله
│
▼
بررسی MAC2 (کوکی گردشی)
├─ معتبر ──► اجرای ضرب اسکالر Curve25519
└─ نامعتبر ──► ارسال Type 3: Cookie Reply (بدون حالت)
در حالت پایدار و زمانی که بار کاری پایینتر از آستانه ماژول ratelimiter.c است، سرور بسته را با بررسی mac1 پذیرفته و فرآیند دستتکانی را به انجام میرساند. اما به محض آنکه حجم ورودی احتمال اشباع پردازنده را پدید آورد، سد دفاعی ثانویه فعال شده و تمام بستههای آغازین ملزم به ارائه برچسب معتبر mac2 مبتنی بر کوکی صادرشده از سرور میشوند.
ساختار احراز هویت دومرحلهای مک (mac1 و mac2)
هر بسته آغازگر وایرگارد دارای دو فیلد ۱۶ بایتی در انتهای ساختار دادهای خود است: mac1 (بایتهای ۱۱۶ تا ۱۳۱) و mac2 (بایتهای ۱۳۲ تا ۱۴۷). این دو فیلد نقش گیتهای مکمل را ایفا میکنند:
۱. گیت mac1: بر اساس فرمول BLAKE2s-128(key = Hash(Label-Mac1 || Responder_PublicKey), message = packet[0..115]) محاسبه میشود. از آنجا که کلید مورد استفاده از کلید عمومی سرور مشتق شده، تنها کلاینتهایی که شناسه واقعی سرور را در اختیار دارند میتوانند برچسب معتبر بسازند. بستههای مربوط به اسکنرهای اینترنتی یا کاوشهای تصادفی در این مرحله رد شده و بدون ارسال پاسخ ICMP بیصدا دور انداخته میشوند.
۲. گیت mac2: بر اساس فرمول BLAKE2s-128(key = Cookie, message = packet[0..131]) تولید میشود. شایان توجه است که دامنه پوشش mac2 کل محتوای بسته شامل فیلد تاییدشده mac1 را در بر میگیرد. کلید ۱۶ بایتی به کار رفته در اینجا یک کوکی رمزنگاری کوتاهمدت است که سرور فقط به نشانیهای آیپی دارای مالکیت تاییدشده اعطا میکند.
در جریان ترافیک عادی شبکه، کلاینت فیلد mac2 را با شانزده بایت صفر (0x00) پر میکند. هنگامی که سرور در وضعیت دفاع در برابر سربار قرار میگیرد، بستههای حاوی بایتهای صفر یا مقادیر نادرست از ورود به چرخه محاسباتی پردازنده منع میشوند. در این حالت سرور بدون ایجاد دادههای وضعیت در حافظه، یک زنجیره چالش و پاسخ بدون حالت را به جریان میاندازد.
سازوکار درونی cookie.c در هسته لینوکس: چالش و پاسخ بدون حالت
هنگامی که ماژول ratelimiter.c اعلام اضافه بار میکند، تابع wg_cookie_checker_create_payload() در فایل cookie.c کنترل ارتباط را به دست میگیرد. هسته سیستمعامل یک بسته ۶۴ بایتی از نوع Type 3: Handshake Cookie Reply را با ساختاری مشخص تولید میکند:
┌────────────────────────────────────────────────────────┐
│ نوع بسته: ۳ (۱ بایت) │ فیلد رزرو: ۰ (۳ بایت) │
├────────────────────────────────────────────────────────┤
│ نمایه گیرنده: بازتاب sender_index کلاینت (۴ بایت) │
├────────────────────────────────────────────────────────┤
│ مقدار یکبارمصرف XChaCha20 Nonce: از CSPRNG (۲۴ بایت) │
├────────────────────────────────────────────────────────┤
│ توکن کوکی رمزگذاریشده: XChaCha20-Poly1305 (۳۲ بایت) │
│ - ۱۶ بایت کوکی آشکار │
│ - ۱۶ بایت برچسب اصالتسنجی Poly1305 │
└────────────────────────────────────────────────────────┘
ایجاد این بسته پاسخ به کمترین چرخه محاسباتی پردازنده نیاز دارد. نکته بنیادین این است که سرور در طول این فرآیند هیچگونه حافظه پویایی روی هیپ (kmalloc = 0) اختصاص نمیدهد. بسته خروجی شاخص sender_index کلاینت را بازتاب میدهد تا کلاینت بداند پاسخ به کدام تلاش پیوند دارد، در حالی که توکن حساس کوکی با الگوریتم XChaCha20-Poly1305 رمزگذاری شده است.
کلید رمزنگاری متقارن کوکی با یک فرآیند قطعی محاسبه میگردد:
Cookie_Encryption_Key = BLAKE2s-256(
key = Hash(Label-Cookie || Responder_PublicKey),
message = Initiator_MAC1
)
از آنجا که مقدار Initiator_MAC1 پیشتر توسط سرور تایید اعتبار شده، به منزله یک نمک رمزنگاری منحصربهفرد برای آن اتصال عمل کرده و مانع از محاسبه زودهنگام کلید رمزگشایی توسط شنودکنندگان میشود.
چرخش آنتروپی راز و اثبات مالکیت نشانی آیپی
ارزش امنیتی بنیادین وایرگارد در این نهفته است که بدون ثبت سوابق، مالکیت نشانی فرستنده را به اثبات میرساند. سرور کوکی را بر اساس یک راز ۳۲ بایتی درون هسته (cookie_checker->secret) که توسط مولد تصادفی امن لینوکس (get_random_bytes) تولید شده مشتق میکند.
فرمول محاسبه، نشانی فیزیکی فرستنده را مستقیما به کوکی گره میزند:
Cookie = BLAKE2s-128(
key = cookie_checker->secret,
message = Initiator_IP_Address || Initiator_Port
)
برای خنثی کردن راهبرد ذخیرهسازی و بازپخش کوکیها توسط مهاجمان، سرور هر ۱۲۰ ثانیه یک بار این کلید محرمانه را تغییر میدهد (COOKIE_SECRET_MAX_AGE = 120).
برای تابآوری در برابر نوسانات تاخیر شبکه و بستههای معلق در مسیر، ماژول cookie.c دو نسل از کلیدهای محرمانه را همزمان نگهداری میکند:
secret[0]: کلید جاری فعال جهت تولید کوکیهای تازه و اعتبارسنجی بستههای نو رسیده.secret[1]: کلید پیشین مربوط به بازه ۱۲۰ ثانیهای گذشته جهت تایید درخواستهایی که در مرز تغییر کلید ارسال شدهاند.
در سناریوی حمله جعل نشانی، سرور بستههای Type 3: Cookie Reply را از طریق پروتکل UDP به همان نشانیهای جعلی برمیگرداند. از آنجا که مهاجم مالکیتی بر روی آن نشانیها ندارد، هرگز قادر به رویت یا رمزگشایی کوکی نخواهد بود.
اما کلاینت قانونی به محض دریافت پاسخ، تابع wg_cookie_message_consume() را اجرا کرده، توکن را رمزگشایی و در حافظه موقت خود (peer->latest_cookie) قرار میدهد، برچسب زمانی cookie_birthdate = jiffies را ثبت میکند و بلافاصله بسته آغاز دستتکانی را به همراه فیلد پرشده mac2 دوباره میفرستد. سرور صحت mac2 را در زمان ثابت O(1) تایید کرده، از تعلق آیپی به فرستنده مطمئن میشود و سپس وارد فرآیند Curve25519 میگردد.
همزمانی بدون قفل و معماری RiceGuard
توان پردازشی چشمگیر ماژول cookie.c به دلیل ساختار بدون قفل (Lockless) آن به دست آمده است. خواندن کلیدهای محرمانه و محاسبه برچسبهای تایید اصالت تماما درون بخش بحرانی rcu_read_lock() انجام میگیرد. حذف قفلهای سراسری اسپینلاک در مسیر دریافت بستهها به همه هستههای پردازنده امکان میدهد فیلدهای mac1 و mac2 را به گونهای همزمان و با بالاترین بازده بررسی کنند.
بسته ورودی ──► [صف دریافت کارت شبکه] ──► خواندن بدون قفل RCU ──► بررسی اصالت BLAKE2s ──► ریسه پردازشی هسته
در مقیاسهای عملیاتی سنگین، درگاههای ارتباطی با هجوم میلیونها بسته در هر ثانیه مواجه میشوند. در VPNRice، موتور پیشرفته RiceGuard با ادغام منطق cookie.c در راهکارهای eBPF و فناوری شتابدهنده سختافزاری XDP، پدافند شبکه را تقویت میکند.
با منتقل کردن بررسی فیلدهای دومرحلهای مک به لایه درایور پیش از تخصیص بافرهای سوکت sk_buff، سیستم ریسگارد امواج جعلی را در نقطه ورود فیزیکی دفع میکند. بدین ترتیب کاربران با بهرهمندی از رازداری مستقیم و کمترین میزان تاخیر، اتصالی امن و همواره پایدار را تجربه مینمایند.



