The critical vulnerability recently disclosed by cloud security firm Orca impacts Google Kubernetes Engine (GKE) and could allow threat actors with a Google account to take control of a Kubernetes cluster. Estimates show that up to 250,000 active GKE clusters could be susceptible to this attack vector, dubbed Sys:All. According to security researcher Roi Nisimi, the problem "stems from a likely widespread misconception that the system:authenticated group in Google Kubernetes Engine includes only verified and deterministic identities, whereas in fact, it includes any Google authenticated account (even outside the organization)."
The system:authenticated group is a special group in Kubernetes. It includes all authenticated entities — both human users and service accounts. If, or when, administrators allow overly permissive roles, the consequences could be significant. That means that a threat actor could use their own Google OAuth 2.0 bearer token to take control of the cluster and potentially carry out further exploits, including theft of sensitive data, crypto mining, denial of service attacks, or lateral movement.
Although Google took steps to block the binding of the system:authenticated group to the cluster-admin role in GKE versions 1.28 and later and Google notes that granting Kubernetes privileges to the system:authenticated group violates the principle of least privilege, it’s important to make sure that your organization is not impacted by this issue if you’re using an older version of GKE.
As soon as we learned of this critical Kubernetes vulnerability in GKE, we took steps to make sure our customers were not impacted. For our managed services customers, we immediately used our tooling to look for any offending custom role bindings. Happily, we didn’t find any. For anyone who would like to review this information themselves, we recommend following Google’s guide for reviewing the role bindings or using rbac-lookup:
```rbac-lookup system:authenticated -owide
rbac-lookup system:unauthenticated -owide
rbac-lookup system:anonymous -owide```
Our own execution of these commands shows that only the expected default bindings exist to the system:authenticated, system:unauthenticated, and system:anonymous groups.
Evaluating our managed Kubernetes environments for the vulnerability is important, but we also wanted to make sure that this capability was available to all Fairwinds Insights customers. We quickly created two Open Policy Agent (OPA) policies last week that any Insights user can use to determine whether this issue exists in their Kubernetes clusters and prevent anyone from creating RBAC policies that could expose the cluster to this attack..
Here’s the logic we used to enforce these checks within Fairwinds Insights, using our OPA plugin:
package fairwinds
isAllowedClusterRoleBindingRoleRef(roleRefName) {
allowedRoleRefNames := {"system:basic-user", "system:discovery", "system:public-info-viewer"}
allowedRoleRefNames[roleRefName]
}
checkClusterRoleBinding[actionItem] {
input.kind == "ClusterRoleBinding"
defaultSubjects := {"system:anonymous", "system:unauthenticated", "system:authenticated"}
inputSubjectsSet := {x | x = input.subjects[_]}
count(defaultSubjects - inputSubjectsSet) == count(defaultSubjects)
roleRefName := input.roleRef.name
not isAllowedClusterRoleBindingRoleRef(roleRefName)
actionItem := {
"title": "Insecure GKE ClusterRoleBinding",
"description": sprintf("ClusterRoleBinding %s references a default role",[input.metadata.name]),
"remediation": "Only the expected default bindings should exist to the `system:authenticated`, `system:unauthenticated`, and `system:anonymous` groups.",
"category": "Security",
"severity": .99,
}
}
gke-insecure-default-rolebinding
package fairwinds
checkRoleBinding[actionItem] {
input.kind == "RoleBinding"
subject := input.subjects[_]
defaultSubjects := {"system:anonymous", "system:unauthenticated",
"system:authenticated"}
defaultSubjects[_] = subject.name
actionItem := {
"title": "Insecure GKE RoleBinding",
"description": sprintf("RoleBinding %s contains default system subject", [input.metadata.name]),
"remediation": "There should be no RoleBinding that references `system:authenticated`, `system:unauthenticated`, and `system:anonymous` groups.",
"category": "Security",
"severity": .99,
}
}
If you’re not already an Insights user, you can sign up for insights for free to check if you are vulnerable. Install the OPA report in the Install Hub to check for the vulnerability, and make sure you install these two new OPA policies.
If you get stuck installing Insights or have questions, let us know. You can also ask questions in the Fairwinds Community Slack group.