Commit fa25287458
Unregistered key
Layout: unified · split
content/blog/2026-02-21-auditing-aws-passwords.org +26 −22
| @@ -29,11 +29,12 @@ testing. | ||
| 29 | 29 | |
| 30 | 30 | The process runs in two steps: |
| 31 | 31 | 1. ~gather_policy.sh~ calls the AWS CLI to fetch the current IAM password policy, |
| 32 | captures metadata (timestamp, AWS account, region, caller identity), and writes | |
| 33 | everything to a JSON file. This file is evidence of the policy's current state. | |
| 34 | 2. ~evaluate_policy.py~ reads that JSON file, prompts you for the expected value of | |
| 35 | each setting, and exports a CSV report with a value of ~PASS~ or ~FAIL~ for each | |
| 36 | rule. | |
| 32 | captures metadata (timestamp, AWS account, region, caller identity), and | |
| 33 | writes everything to a JSON file. This file is evidence of the policy's | |
| 34 | current state. | |
| 35 | 2. ~evaluate_policy.py~ reads that JSON file, prompts you for the expected value | |
| 36 | of each setting, and exports a CSV report with a value of ~PASS~ or ~FAIL~ for | |
| 37 | each rule. | |
| 37 | 38 | |
| 38 | 39 | * Prerequisites |
| 39 | 40 | |
| @@ -182,32 +183,35 @@ allows you to prove that the data was not modified after the script was run. | ||
| 182 | 183 | * Common Exceptions and False Positives |
| 183 | 184 | |
| 184 | 185 | - *No policy defined*: If ~gather_policy.sh~ exits with a ~NoSuchEntity~ error, the |
| 185 | account has no IAM password policy configured. If you were expecting a password | |
| 186 | policy, document it as a missing control. | |
| 186 | account has no IAM password policy configured. If you were expecting a | |
| 187 | password policy, document it as a missing control. | |
| 187 | 188 | - *HardExpiry: false*: This setting controls whether users are locked out |
| 188 | immediately when their password expires or given a grace period to change it. | |
| 189 | ~false~ is often intentional to avoid lockouts. Check the organization's policy | |
| 190 | before calling it a finding. Additionally, check if the organization has | |
| 191 | security exceptions in place before noting a deficiency. | |
| 189 | immediately when their password expires or given a grace period to change it. | |
| 190 | ~false~ is often intentional to avoid lockouts. Check the organization's policy | |
| 191 | before calling it a finding. Additionally, check if the organization has | |
| 192 | security exceptions in place before noting a deficiency. | |
| 192 | 193 | - *MaxPasswordAge and forced rotation*: A 90-day rotation requirement is common in |
| 193 | older policies and frameworks like CIS. NIST 800-63B no longer recommends forced | |
| 194 | rotation unless there's evidence of compromise. Know which framework you're | |
| 195 | auditing against before writing up a finding for this setting. Confirm with the | |
| 196 | organization to understand which framework they used to write their policy. | |
| 197 | - *PasswordReusePrevention*: AWS allows a maximum of 24 previous passwords. If your | |
| 198 | organization's policy requires a higher number than AWS supports, document the | |
| 199 | platform limitation rather than raising it as a deficiency. | |
| 194 | older policies and frameworks like CIS. NIST 800-63B no longer recommends | |
| 195 | forced rotation unless there's evidence of compromise. Know which framework | |
| 196 | you're auditing against before writing up a finding for this setting. Confirm | |
| 197 | with the organization to understand which framework they used to write their | |
| 198 | policy. | |
| 199 | - *PasswordReusePrevention*: AWS allows a maximum of 24 previous passwords. If | |
| 200 | your organization's policy requires a higher number than AWS supports, | |
| 201 | document the platform limitation rather than raising it as a deficiency. | |
| 200 | 202 | |
| 201 | 203 | * How to Write Up the Finding |
| 202 | 204 | |
| 203 | 205 | If a setting fails, here's how to frame it: |
| 204 | - *Deficiency:* The ~MinimumPasswordLength~ setting in the AWS IAM password policy is | |
| 205 | configured to ~6~, which is below the organization's requirement of ~8~ characters. | |
| 206 | ||
| 207 | - *Deficiency:* The ~MinimumPasswordLength~ setting in the AWS IAM password policy | |
| 208 | is configured to ~6~, which is below the organization's requirement of ~8~ | |
| 209 | characters. | |
| 206 | 210 | - *Root Cause:* Due to {{ root cause }}, the policy was configured to enforce a |
| 207 | 211 | ~MinimumPasswordLength~ of ~6~. |
| 208 | 212 | - *Risk:* Shorter passwords are more susceptible to brute-force and credential |
| 209 | stuffing attacks, increasing the likelihood of unauthorized access to the AWS | |
| 210 | console. | |
| 213 | stuffing attacks, increasing the likelihood of unauthorized access to the AWS | |
| 214 | console. | |
| 211 | 215 | - *Evidence:* Refer to ~policy_audit_<timestamp>.csv~ for documentation of testing. |
| 212 | 216 | |
| 213 | 217 | The same structure applies to any other failing rule. For boolean settings, the |