Home› Blog› AWS Architecture Series #74 — The low findings are what make the critical one…
AWS Architecture AWS Architecture Series

AWS Architecture Series #74 — The low findings are what make the critical one

A GuardDuty backlog gets triaged by severity, and the low-severity findings get a suppression rule because nobody is going to action a port scan. The severity is a risk estimate for that finding in isolation — and the findings being suppressed are the same ones the detector correlates into the critical severity level, which is defined as an attack sequence.

Verified against current vendor documentation on 6 October 2026. Pricing, limits and API behaviour were checked against the official docs on that date. Cloud services change fast — if you are reading this much later, treat the specifics as a starting point and re-check the linked sources.

Business Challenge

#43 built the account that receives these findings and #45 covered turning detection on across an organisation. Both leave you with the same problem: a queue, and a severity number next to each item.

The number is honest about what it is: “Each GuardDuty finding has an assigned severity level and value that reflects the potential risk the finding could have to your environment, as determined by our security engineers. The value of the severity can fall anywhere within the 1.0 to 10.0 range.”

A risk estimate for that finding, by itself. Not a queue position, and not a statement about what the finding might become.

1Suppressing low findings removes the inputs to the critical band

Read the definition of critical severity carefully: “A critical severity level indicates that an attack sequence may be in progress or had recently happened. One or more AWS resources… are potentially being compromised or may have already been compromised.”

An attack sequence is a correlated finding. And suppression rules take findings out of that correlation: “When you create suppression rules that archive findings, Extended Threat Detection can't use these archived findings when correlating events for attack sequences. Broad suppression rules might impact the ability of GuardDuty to detect behaviors aligned with detecting multi-stage attacks. Findings that are archived because of suppression rules are not considered as signals for attack sequences.”

AWS supplies the worked example, and it is the obvious rule somebody writes on a noisy Tuesday: “if you create a suppression rule that archives all EKS cluster-related findings instead of targeting specific known activities, GuardDuty won't be able to use those findings to detect an attack sequence where a threat actor exploits a container, obtains privileged tokens, and accesses sensitive resources.”

So the triage instinct inverts. The findings that look least worth actioning individually are candidate signals for the band GuardDuty asks you to prioritise above everything else.

Fix

Scope rules to behaviours, not to finding types or resource classes. AWS's own guidance: “Keep the suppression rules focused on specific behaviors for which you don't want GuardDuty to generate a finding.”

2Suppression also silences four downstream systems and a malware scan

“Suppressed findings are not sent to AWS Security Hub CSPM, Amazon Simple Storage Service, Amazon Detective, or Amazon EventBridge, reducing finding noise level if you consume GuardDuty findings via Security Hub CSPM, a third-party SIEM, or other alerting and ticketing applications.”

That is the intended effect for a SIEM, and it is a side effect everywhere else. Your S3 export is your long-term evidence store. Detective is where somebody goes to build a timeline during an incident. A suppression rule written to quiet a ticket queue removes the finding from both.

And one more, which is easy to miss because it is a different product: “If you've enabled Malware Protection for EC2, the suppressed GuardDuty findings won't initiate a malware scan.” A suppression rule can therefore turn off scanning for the exact activity that would have triggered it.

Fix

Before writing a rule, enumerate who consumes findings. The finding survives in GuardDuty for 90 days either way, so suppression buys inbox quiet at the cost of every other consumer.

3A filter is not a suppression rule, and the default is the harmless one

In the API they are the same object with one field different. CreateFilter's action parameter has “Valid Values: NOOP | ARCHIVE” and “Default: NOOP”.

So a filter created without action is a saved view — it changes what you see and nothing else. Set it to ARCHIVE and the same criteria become a suppression rule with all the consequences above. One field, in a parameter that is “Required: No”, separates a console convenience from a detection change.

Worth knowing in the other direction too: if you inherited Terraform with action = "ARCHIVE" on something described as a filter, it is suppressing.

Fix

Audit every GuardDuty filter for action. The ones set to ARCHIVE are the detection configuration; the rest are bookmarks.

Architecture

Four bands over one continuous range, and a filter mechanism that addresses them as integers.

Diagram: what a GuardDuty finding's severity encodes, and what a suppression rule actually removes. Each finding has a severity value anywhere in the 1.0 to 10.0 range reflecting the potential risk that finding could have to the environment, as determined by AWS security engineers, and GuardDuty divides the range into four bands. Low is 1.0 to 3.9 and indicates attempted suspicious activity that did not compromise the environment, for example a port scan or a failed intrusion attempt, with no immediate recommended action though it may indicate someone is looking for weak points. Medium is 4.0 to 6.9 and indicates suspicious activity deviating from normally observed behaviour that may be indicative of a resource compromise, with a recommendation to investigate at the earliest convenience and to consider the resource compromised if the activity cannot be confirmed as authorised. High is 7.0 to 8.9 and indicates the resource in question is compromised and actively being used for unauthorized purposes. Critical is 9.0 to 10.0 and indicates an attack sequence may be in progress or recently happened, with one or more resources potentially or already compromised, and GuardDuty recommends prioritising triage and remediation of all critical findings because they can be part of a ransomware attack and can escalate at any time. A key qualifier is that a finding of a particular type may have a different severity depending on the context specific to the finding, so severity is a property of the occurrence rather than of the type, and each type has a default severity listed separately. The central warning records the inversion: critical severity is defined in terms of an attack sequence, attack sequences are correlated from other findings, and AWS states that findings archived because of suppression rules are not considered as signals for attack sequences, that Extended Threat Detection cannot use archived findings when correlating events, and that broad suppression rules might impact the ability to detect multi-stage attacks. The worked example given is that a rule archiving all EKS cluster-related findings instead of targeting specific known activities prevents GuardDuty detecting an attack sequence where a threat actor exploits a container, obtains privileged tokens and accesses sensitive resources. A panel lists everything a suppression rule removes a finding from: Security Hub CSPM, Amazon S3, Amazon Detective and Amazon EventBridge, and if Malware Protection for EC2 is enabled the suppressed findings will not initiate a malware scan; the finding is still generated but marked archived and retained in GuardDuty for ninety days, viewable through ListFindings with a findingCriteria criterion of service.archived equal to true. A mechanism panel notes that in the API a filter and a suppression rule are the same object differing in one field, because the CreateFilter action parameter takes NOOP or ARCHIVE and defaults to NOOP, that the maximum number of saved filters per account per Region is one hundred, and that the rank parameter from one to one hundred sets both the filter's position in the list and the order in which it is applied to findings. A further note records that severity-based filter criteria are expressed as integers rather than the decimal severity value, with Low as one two three, Medium as four five six, High as seven eight, and Critical as nine ten. A closing panel records AWS's guidance to build suppression rules reactively and only for findings for which false positives have repeatedly been identified, to keep rules focused on specific behaviours, that only the GuardDuty administrator can create suppression rules in a multi-account environment, and the documented examples including the on-premises egress gateway case for instance credential exfiltration, the bastion host case for SSH brute force, and the duplicate DNS findings caused by Kubernetes clusters running their own DNS server pods so that each pod lookup produces two DNS events.
Severity describes one finding. The critical band describes several, correlated.

The four bands, and the qualifier under them

Band Value range What AWS says it means Recommended response
Critical 9.0 – 10.0 “an attack sequence may be in progress or had recently happened” Prioritise all of them — “can be a part of a ransomware attack and can escalate at any time”
High 7.0 – 8.9 “the resource in question… is compromised and is actively being used for unauthorized purposes” Immediate remediation
Medium 4.0 – 6.9 “suspicious activity that deviates from normally observed behavior” Investigate at earliest convenience; if unconfirmed, “consider the resource compromised”
Low 1.0 – 3.9 “attempted suspicious activity that did not compromise your environment” “no immediate recommended action”, but worth noting

And the sentence that answers why the same alert arrives with two different numbers on two different days: “A finding of a particular type may have a different severity depending on the context specific to the finding.”

Severity is therefore a property of the occurrence, not of the type. A per-type default list exists, but the number on the finding in front of you has already been adjusted for context. Which means a runbook keyed on finding type is keyed on the wrong thing, and a dashboard counting "how many High" is counting a population whose membership shifts.

The filter addresses severity as an integer

The bands are decimal, and the filter criteria are not: “To configure severity based filters, use the following for the FindingCriteria condition: Low: ["1", "2", "3"]… Medium: ["4", "5", "6"]… High: ["7", "8"]… Critical: ["9", "10"].”

The integer buckets line up exactly with the decimal bands — 7 and 8 cover 7.0 through 8.9 — so there is no gap. What there is, is a mismatch between the value you read in the console and the value you write in a rule. Somebody copying 8.5 out of a finding into a filter is writing a criterion against a different representation than the one the page documents.

The finding is not deleted, and that is the useful part

“GuardDuty continues to generate findings even when they match your suppression rules, however, those findings are automatically marked as archived. The archived finding is stored in GuardDuty for 90 days and can be viewed at any time during that period.” So a suppression rule is a routing decision rather than a detection one — the detector keeps working and the record keeps existing. What stops is delivery, and participation in correlation. You can read what you suppressed via ListFindings with service.archived equal to true, which is the single most useful query for auditing your own rules.

Why This Architecture Holds Up

AWS's guidance is unusually restrictive, and the reason is now visible

Marked Important in the documentation: “GuardDuty recommends that you build suppression rules reactively and only for findings for which you have repeatedly identified false positives in your environment.”

Three constraints in one sentence — after the fact, only for false positives, and only for repeated ones. That rules out the whole category of pre-emptive noise reduction, which is how most suppression rules actually get written: during onboarding, from a list of finding types somebody expects to be noisy.

Read alongside the attack-sequence consequence, the restriction stops looking conservative. A rule built pre-emptively over a finding type is exactly the broad rule that removes signals, and it is built before anyone has seen a single false positive to justify it.

The documented examples share a shape worth copying

Every example AWS gives pairs a finding type with a second criterion that identifies the specific legitimate cause:

  • UnauthorizedAccess:IAMUser/InstanceCredentialExfiltration.OutsideAWS plus the API caller IPv4 address of your on-premises gateway — for the case where “VPC networking is configured to route internet traffic such that it egresses from an on-premises gateway rather than from a VPC Internet Gateway”.
  • UnauthorizedAccess:EC2/SSHBruteForce plus an instance image ID or tag value identifying your bastion hosts, because “If the target of the brute force attempt is a bastion host, this may represent expected behavior for your AWS environment.”
  • Recon:EC2/Portscan plus the instances “that host these vulnerability assessment tools”.

Not one of them is the finding type alone — and that is a choice in the examples rather than a restriction in the product. AWS is explicit that both shapes are available: “You can configure suppression rules to suppress entire finding types, or define more granular filter criteria to suppress only specific instances of a particular finding type.”

So the broad rule is permitted and the narrow one is what gets demonstrated. The second criterion is what turns "stop telling me about brute force" into "stop telling me about brute force against the host whose job is to absorb it" — and it is what leaves the same finding type live everywhere else, where it can still act as a signal.

The Kubernetes DNS case is a true duplicate, and it is the clearest legitimate use

“Kubernetes clusters run their own DNS servers as pods, such as coredns. Therefore, for each DNS lookup from a pod, GuardDuty captures two DNS events — one from the pod and the other from the server pod.” AWS lists eleven DNS finding types this can duplicate, and the recommended rule pairs the finding type with the DNS server's own executablePath or executableSha256. That is suppression of a mechanical artefact rather than of a risk judgement, which is the distinction worth holding: you are removing the second copy of an event, not deciding the event does not matter.

Two operational limits on the mechanism itself

“The maximum number of saved filters per AWS account per Region is 100.” Since specific rules are the recommended kind, and specific rules are numerous, the ceiling and the guidance pull against each other — one rule per legitimate cause per Region adds up faster than it sounds.

And filters are ordered: “rank… Specifies the position of the filter in the list of current filters. Also specifies the order in which this filter is applied to the findings”, with a range of 1 to 100. So the mechanism has precedence, which means two overlapping rules are not commutative and the order is a thing you set rather than a thing you discover.

And in an organisation, this is one person's decision

“In a multi-account environment only the GuardDuty administrator can create suppression rules.” Correct design — suppression is a detection change and should not be delegated to the account generating the noise. The consequence is that the request comes from the team with the context and the decision sits with the team without it, so the administrator needs the second criterion from the requester rather than just a finding type.

Key Architecture Decisions

Decision Choice Reasoning
Rule scope Finding type plus a criterion identifying the legitimate cause Every documented example does this; type-only rules are the broad ones that remove attack-sequence signals.
When to write a rule Reactively, after repeated false positives AWS's stated recommendation, and pre-emptive rules are necessarily the broad kind.
Low-severity noise Route elsewhere rather than suppress Suppressed findings are not considered as signals for attack sequences, and critical severity is defined as an attack sequence.
Before any rule Enumerate the consumers Suppression removes the finding from Security Hub CSPM, S3, Detective and EventBridge at once.
Malware Protection for EC2 enabled Treat suppression as scan suppression too Suppressed findings won't initiate a malware scan.
Existing filters Audit the action field NOOP is a saved view; ARCHIVE is detection configuration. The default is NOOP.
Severity in filter criteria Integers, per the documented mapping Bands are decimal (7.0–8.9) but criteria are written as ["7", "8"].
Runbooks Key on severity and context, not on finding type The same type may arrive with a different severity depending on context.
Overlapping rules Set rank deliberately It determines the order in which filters are applied.
Kubernetes DNS duplicates Suppress on the DNS pod's executable path or SHA-256 Each pod lookup produces two events; this removes the mechanical duplicate, not the judgement.

The audit worth running

ListFindings with service.archived equal to true, over the last 90 days. That is the record of what your rules decided you would not see, and reading it is how you find out whether a rule written eighteen months ago is now archiving something that matters — which reviewing the rules themselves will not tell you, because a rule's text does not change when your environment does.

Then read every filter's action and its criteria count. A rule whose criteria are a finding type and nothing else is the shape AWS warns about, regardless of what it was written for.

Closing Thought

The severity number is doing a narrower job than its presentation suggests. It is an estimate of the risk that finding carries, which is why a port scan is a 2 and why the recommendation for a 2 is to take note and do nothing. That is reasonable advice about the finding and bad advice about the queue, because the detector is also reading those 2s as material for something else.

So the useful reframe is that triage has two outputs, not one. Whether a human should look at this now is a severity question. Whether GuardDuty should keep seeing findings like this is a different question entirely, and the suppression rule answers the second while appearing to answer the first.

Which lands in the same place this block keeps landing. #72 was a resource accumulating against a ceiling. #73 was a schedule quietly not running. This one is a detection capability quietly reduced by a change made for inbox hygiene — documented, intended, and invisible from the dashboard that motivated it.

Next in this series

Security & Identity — Security Hub control findings: why a control can be passing on a resource that is non-compliant, what consolidated control findings changed about counting, and why the security score is not a percentage of your risk.

Comments

How was your experience?
Your feedback helps improve this site.
PoorExcellent