Skip to content

Commit

Permalink
Update queries to check policy attachment & separation to validate al…
Browse files Browse the repository at this point in the history
…l vs custom iam policies. Fixes #277 Closes #280 (#281)
  • Loading branch information
rajlearner17 committed Sep 27, 2021
1 parent 8567d91 commit b59a904
Show file tree
Hide file tree
Showing 6 changed files with 93 additions and 20 deletions.
2 changes: 1 addition & 1 deletion cis_v130/section_1.sp
Original file line number Diff line number Diff line change
Expand Up @@ -247,7 +247,7 @@ control "cis_v130_1_15" {
control "cis_v130_1_16" {
title = "1.16 Ensure IAM policies that allow full \"*:*\" administrative privileges are not attached"
description = "IAM policies are the means by which privileges are granted to users, groups, or roles. It is recommended and considered a standard security advice to grant least privilege -that is, granting only the permissions required to perform a task. Determine what users need to do and then craft policies for them that let the users perform only those tasks, instead of allowing full administrative privileges."
sql = query.iam_policy_no_star_star.sql
sql = query.iam_all_policy_no_star_star.sql
documentation = file("./cis_v130/docs/cis_v130_1_16.md")

tags = merge(local.cis_v130_1_common_tags, {
Expand Down
2 changes: 1 addition & 1 deletion cis_v140/section_1.sp
Original file line number Diff line number Diff line change
Expand Up @@ -246,7 +246,7 @@ control "cis_v140_1_15" {
control "cis_v140_1_16" {
title = "1.16 Ensure IAM policies that allow full \"*:*\" administrative privileges are not attached"
description = "IAM policies are the means by which privileges are granted to users, groups, or roles. It is recommended and considered a standard security advice to grant least privilege -that is, granting only the permissions required to perform a task. Determine what users need to do and then craft policies for them that let the users perform only those tasks, instead of allowing full administrative privileges."
sql = query.iam_policy_no_star_star.sql
sql = query.iam_all_policy_no_star_star.sql
documentation = file("./cis_v140/docs/cis_v140_1_16.md")

tags = merge(local.cis_v140_1_common_tags, {
Expand Down
4 changes: 2 additions & 2 deletions foundational_security/iam.sp
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ control "foundational_security_iam_1" {
title = "1 IAM policies should not allow full '*' administrative privileges"
description = "This control checks whether the default version of IAM policies (also known as customer managed policies) has administrator access that includes a statement with 'Effect': 'Allow' with 'Action': '*' over 'Resource': '*'. The control only checks the customer managed policies that you create. It does not check inline and AWS managed policies."
severity = "high"
sql = query.iam_policy_no_star_star.sql
sql = query.iam_custom_policy_no_star_star.sql
documentation = file("./foundational_security/docs/foundational_security_iam_1.md")

tags = merge(local.foundational_security_iam_common_tags, {
Expand Down Expand Up @@ -129,7 +129,7 @@ control "foundational_security_iam_21" {
title = "21 IAM customer managed policies that you create should not allow wildcard actions for services"
description = "This control checks whether the IAM identity-based policies that you create have Allow statements that use the * wildcard to grant permissions for all actions on any service. The control fails if any policy statement includes 'Effect': 'Allow' with 'Action': 'Service:*'."
severity = "low"
sql = query.iam_custom_policy_no_star_star.sql
sql = query.iam_custom_policy_no_service_wild_card.sql
documentation = file("./foundational_security/docs/foundational_security_iam_21.md")

tags = merge(local.foundational_security_iam_common_tags, {
Expand Down
34 changes: 34 additions & 0 deletions query/iam/iam_all_policy_no_star_star.sql
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
with star_access_policies as (
select
arn,
count(*) as num_bad_statements
from
aws_iam_policy,
jsonb_array_elements(policy_std -> 'Statement') as s,
jsonb_array_elements_text(s -> 'Resource') as resource,
jsonb_array_elements_text(s -> 'Action') as action
where
s ->> 'Effect' = 'Allow'
and resource = '*'
and (
(action = '*'
or action = '*:*'
)
)
and attachment_count !=0
group by arn
)
select
-- Required Columns
p.arn as resource,
case
when s.arn is null then 'ok'
else 'alarm'
end status,
p.name || ' contains ' || coalesce(s.num_bad_statements,0) ||
' statements that allow action "*" on resource "*".' as reason,
-- Additional Dimensions
p.account_id
from
aws_iam_policy as p
left join star_access_policies as s on p.arn = s.arn;
33 changes: 33 additions & 0 deletions query/iam/iam_custom_policy_no_service_wild_card.sql
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
with wildcard_action_policies as (
select
arn,
count(*) as statements_num
from
aws_iam_policy,
jsonb_array_elements(policy_std -> 'Statement') as s,
jsonb_array_elements_text(s -> 'Resource') as resource,
jsonb_array_elements_text(s -> 'Action') as action
where
is_aws_managed = 'false'
and s ->> 'Effect' = 'Allow'
and resource = '*'
and action like '%:*'
group by
arn
)
select
-- Required Columns
a.arn as resource,
case
when b.arn is null then 'ok'
else 'alarm'
end status,
a.name || ' contains ' || coalesce(b.statements_num,0) ||
' statements that allow action "Service:*" on resource "*".' as reason,
-- Additional Dimensions
a.account_id
from
aws_iam_policy as a
left join wildcard_action_policies as b on a.arn = b.arn
where
a.arn not like 'arn:aws:iam::aws:policy%';
38 changes: 22 additions & 16 deletions query/iam/iam_custom_policy_no_star_star.sql
Original file line number Diff line number Diff line change
@@ -1,33 +1,39 @@
with wildcard_action_policies as (
-- This query checks the customer managed policies having * access and attached to IAM resource(s)
with star_access_policies as (
select
arn,
count(*) as statements_num
count(*) as num_bad_statements
from
aws_iam_policy,
jsonb_array_elements(policy_std -> 'Statement') as s,
jsonb_array_elements_text(s -> 'Resource') as resource,
jsonb_array_elements_text(s -> 'Action') as action
where
is_aws_managed = 'false'
and s ->> 'Effect' = 'Allow'
s ->> 'Effect' = 'Allow'
and resource = '*'
and action like '%:*'
group by
arn
)
and (
(action = '*'
or action = '*:*'
)
)
-- Checking attachment
and attachment_count !=0
group by arn
)
select
-- Required Columns
a.arn as resource,
p.arn as resource,
case
when b.arn is null then 'ok'
when s.arn is null then 'ok'
else 'alarm'
end status,
a.name || ' contains ' || coalesce(b.statements_num,0) ||
' statements that allow action "Service:*" on resource "*".' as reason,
p.name || ' contains ' || coalesce(s.num_bad_statements,0) ||
' statements that allow action "*" on resource "*".' as reason,
-- Additional Dimensions
a.account_id
p.account_id
from
aws_iam_policy as a
left join wildcard_action_policies as b on a.arn = b.arn
aws_iam_policy as p
left join star_access_policies as s on p.arn = s.arn
where
a.arn not like 'arn:aws:iam::aws:policy%'
-- Filter only customer managed policies
p.arn not like 'arn:aws:iam::aws:policy%';

0 comments on commit b59a904

Please sign in to comment.