Comment on page
GCP - Basic Information
Google Cloud uses a Resource hierarchy that is similar, conceptually, to that of a traditional filesystem. This provides a logical parent/child workflow with specific attachment points for policies and permissions.
At a high level, it looks like this:
A virtual machine (called a Compute Instance) is a resource. A resource resides in a project, probably alongside other Compute Instances, storage buckets, etc.
It's possible to migrate a project without any organization to an organization with the permissions
roles/resourcemanager.projectMover. If the project is inside other organization, it's needed to contact GCP support to move them out of the organization first. For more info check this.
Allow to centralize control over your organization's cloud resources:
- Centralize control to configure restrictions on how your organization’s resources can be used.
- Define and establish guardrails for your development teams to stay within compliance boundaries.
- Help project owners and their teams move quickly without worry of breaking compliance.
These policies can be created to affect the complete organization, folder(s) or project(s). Descendants of the targeted resource hierarchy node inherit the organization policy.
In order to define an organization policy, you choose a constraint, which is a particular type of restriction against either a Google Cloud service or a group of Google Cloud services. You configure that constraint with your desired restrictions.
- Limit resource sharing based on domain.
- Limit the usage of Identity and Access Management service accounts.
- Restrict the physical location of newly created resources.
- Disable service account creation
These are like IAM policies in AWS as each role contains a set of permissions.
However, unlike in AWS, there is no centralized repo of roles. Instead of that, resources give X access roles to Y principals, and the only way to find out who has access to a resource is to use the
get-iam-policymethod over that resource. This could be a problem because this means that the only way to find out which permissions a principal has is to ask every resource who is it giving permissions to, and a user might not have permissions to get permissions from all resources.
There are three types of roles in IAM:
- Basic/Primitive roles, which include the Owner, Editor, and Viewer roles that existed prior to the introduction of IAM.
- Predefined roles, which provide granular access for a specific service and are managed by Google Cloud. There are a lot of predefined roles, you can see all of them with the privileges they have here.
- Custom roles, which provide granular access according to a user-specified list of permissions.
You can also search here predefined roles offered by each product. Note that some roles cannot be attached to users and only to SAs because some permissions they contain. Moreover, note that permissions will only take effect if they are attached to the relevant service.
In GCP console there isn't any Users or Groups management, that is done in Google Workspace. Although you could synchronize a different identity provider in Google Workspace.
MFA can be forced to Workspaces users, however, an attacker could use a token to access GCP via cli which won't be protected by MFA (it will be protected by MFA only when the user logins to generate it:
gcloud auth login).
When an organisation is created several groups are strongly suggested to be created. If you manage any of them you might have compromised all or an important part of the organization:
These are the principals that resources can have attached and access to interact easily with GCP. For example, it's possible to access the auth token of a Service Account attached to a VM in the metadata. It is possible to encounter some conflicts when using both IAM and access scopes. For example, your service account may have the IAM role of
compute.instanceAdminbut the instance you've breached has been crippled with the scope limitation of
https://www.googleapis.com/auth/compute.readonly. This would prevent you from making any changes using the OAuth token that's automatically assigned to your instance.
It's similar to IAM roles from AWS. But not like in AWS, any service account can be attached to any service (it doesn't need to allow it via a policy).
Several of the service accounts that you will find are actually automatically generated by GCP when you start using a service, like:
However, it's also possible to create and attach to resources custom service accounts, which will look like this:
Access scope are attached to generated OAuth tokens to access the GCP API endpoints. They restrict the permissions of the OAuth token. This means that if a token belongs to an Owner of a resource but doesn't have the in the token scope to access that resource, the token cannot be used to (ab)use those privileges.
Google actually recommends that access scopes are not used and to rely totally on IAM. The web management portal actually enforces this, but access scopes can still be applied to instances using custom service accounts programmatically.
You can see what scopes are assigned by querying:
"scope": "openid https://www.googleapis.com/auth/userinfo.email https://www.googleapis.com/auth/cloud-platform https://www.googleapis.com/auth/appengine.admin https://www.googleapis.com/auth/sqlservice.login https://www.googleapis.com/auth/compute https://www.googleapis.com/auth/accounts.reauth",
"email": "[email protected]",
The previous scopes are the ones generated by default using
gcloudto access data. This is because when you use
gcloudyou first create an OAuth token, and then use it to contact the endpoints.
The most important scope of those potentially is
cloud-platform, which basically means that it's possible to access any service in GCP.
If you have
gcloudbrowser credentials, it's possible to obtain a token with other scopes, doing something like:
# Maybe you can get a user token with other scopes changing the scopes array from ~/.config/gcloud/credentials.db
# Set new scopes for SDKs credentials
gcloud auth application-default login --scopes=https://www.googleapis.com/auth/userinfo.email,https://www.googleapis.com/auth/cloud-platform,https://www.googleapis.com/auth/sqlservice.login,https://www.googleapis.com/auth/appengine.admin,https://www.googleapis.com/auth/compute,https://www.googleapis.com/auth/accounts.reauth,https://www.googleapis.com/auth/admin.directory.user,https://www.googleapis.com/auth/admin.directory.group,https://www.googleapis.com/auth/admin.directory.domain
# Print new token
gcloud auth application-default print-access-token
# To use this token with some API you might need to use curl to indicate the project header with --header "X-Goog-User-Project: <project-name>"
As defined by terraform in https://registry.terraform.io/providers/hashicorp/google/latest/docs/resources/google_project_iam using terraform with GCP there are different ways to grant a principal access over a resource:
- Memberships: You set principals as members of roles without restrictions over the role or the principals. You can put a user as a member of a role and then put a group as a member of the same role and also set those principals (user and group) as member of other roles.
- Bindings: Several principals can be binded to a role. Those principals can still be binded or be members of other roles. However, if a principal which isn’t binded to the role is set as member of a binded role, the next time the binding is applied, the membership will disappear.
- Policies: A policy is authoritative, it indicates roles and principals and then, those principals cannot have more roles and those roles cannot have more principals unless that policy is modified (not even in other policies, bindings or memberships). Therefore, when a role or principal is specified in policy all its privileges are limited by that policy. Obviously, this can be bypassed in case the principal is given the option to modify the policy or privilege escalation permissions (like create a new principal and bind him a new role).