We recently announced that Microsoft Defender for Cloud now supports Google Cloud Platform (GCP) with its native CSPM and CWPP capabilities, without any dependencies on Google 1st party tools. Learn more about our new release from the blog here. In order to protect your GCP based resources using Microsoft Defender for Coud, follow our step-by-step documentation here.
Microsoft Defender for Cloud implements GCP security recommendations in the Defender for Cloud portal right alongside Azure recommendations. Here is a reference list of all the recommendations Defender for Cloud can provide for GCP resources.
- Ensure that corporate login credentials are used
- Ensure that there are only GCP-managed service account keys for each service account
- Ensure that Service Account has no Admin privileges
- Ensure that IAM users are not assigned the Service Account User or Service Account Token Creator roles at project
- Ensure user-managed/external keys for service accounts are rotated every 90 days or less
- Ensure that Separation of duties is enforced while assigning service account related roles to users
- Ensure that Cloud KMS cryptokeys are not anonymously or publicly accessible
- Ensure KMS encryption keys are rotated within a period of 90 days
- Ensure that Separation of duties is enforced while assigning KMS related roles to users
- Ensure that Cloud Audit Logging is configured properly across all services and all users from a project
- Ensure that sinks are configured for all log entries
- Ensure that retention policies on log buckets are configured using Bucket Lock
- Ensure log metric filter and alerts exist for project ownership assignments/changes
- Ensure that the log metric filter and alerts exist for Audit Configuration changes
- Ensure that the log metric filter and alerts exist for Custom Role changes
- Ensure that the log metric filter and alerts exist for VPC Network Firewall rule changes
- Ensure that the log metric filter and alerts exist for VPC network route changes
- Ensure that the log metric filter and alerts exist for VPC network changes
- Ensure that the log metric filter and alerts exist for Cloud Storage IAM permission changes
- Ensure that the log metric filter and alerts exist for SQL instance configuration changes
- Ensure that the default network does not exist in a project
- Ensure legacy networks do not exist for a project
- Ensure that DNSSEC is enabled for Cloud DNS
- Ensure that RSASHA1 is not used for the key-signing key in Cloud DNS DNSSEC
- Ensure that RSASHA1 is not used for the zone-signing key in Cloud DNS DNSSEC
- Ensure that SSH access is restricted from the internet
- Ensure that RDP access is restricted from the Internet
- Ensure that VPC Flow Logs is enabled for every subnet in a VPC Network
- Ensure no HTTPS or SSL proxy load balancers permit SSL policies with weak cipher suites
- Ensure that instances are not configured to use the default service account
- Ensure that instances are not configured to use the default service account with full access to all Cloud APIs
- Ensure "Block Project-wide SSH keys" is enabled for VM instances
- Ensure oslogin is enabled for a Project
- Ensure oslogin is enabled for all instances
- Ensure 'Enable connecting to serial ports' isnot enabled for VM Instance
- Ensure that IP forwarding is not enabled on Instances
- Ensure VM disks for critical VMs are encrypted with Customer-Supplied Encryption Keys
- Ensure Compute instances are launched with Shielded VM enabled
- Ensure that Compute instances do not have public IP addresses
- Ensure that Cloud Storage bucket is not anonymously or publicly accessible
- Ensure that Cloud Storage buckets have uniform bucket-level access enabled
- Ensure that the 'local_infile' database flag for a Cloud SQL Mysql instance is set to 'off'
- Ensure that the 'log_checkpoints' database flag for Cloud SQL PostgreSQL instance is set to 'on'
- Ensure that the 'log_connections' database flag for Cloud SQL PostgreSQL instance is set to 'on'
- Ensure that the 'log_disconnections' database flag for Cloud SQL PostgreSQL instance is set to 'on'
- Ensure that the 'log_lock_waits' database flag for Cloud SQL PostgreSQL instance is set to 'on'
- Ensure that the 'log_min_messages' database flag for Cloud SQL PostgreSQL instance is set appropriately
- Ensure that the 'log_temp_files' database flag for Cloud SQL PostgreSQL instance is set to '0' (on)
- Ensure that the 'log_min_duration_statement' database flag for Cloud SQL PostgreSQL instance is set to '-1'
- Ensure that the 'cross db ownership chaining' database flag for Cloud SQL SQL Server instance is set to 'off'
- Ensure that the 'contained database authentication' database flag for Cloud SQL on the SQL Server instance is set
- Ensure that the Cloud SQL database instance requires all incoming connections to use SSL
- Ensure that Cloud SQL database instances are not open to the world
- Ensure that Cloud SQL database instances do not have public IPs
- Ensure that Cloud SQL database instances are configured with automated backups
- Ensure that BigQuery datasets are not anonymously or publicly accessible
- Ensure that Cloud DNS logging is enabled for all VPC networks
- Ensure Firewall Rules for instances behind Identity Aware Proxy (IAP) only allow the traffic from Google Cloud Loadbalancer (GCLB) Health Check and Proxy Addresses
- Ensure that Compute instances have Confidential Computing enabled
- Ensure 'skip_show_database' database flag for Cloud SQL Mysql instance is set to 'on'
- Ensure 'log_duration' database flag for Cloud SQL PostgreSQL instance is set to 'on'
- Ensure 'log_hostname' database flag for Cloud SQL PostgreSQL instance is set appropriately
- Ensure 'log_parser_stats' database flag for Cloud SQL PostgreSQL instance is set to 'off'
- Ensure 'log_planner_stats' database flag for Cloud SQL PostgreSQL instance is set to 'off'
- Ensure 'log_executor_stats' database flag for Cloud SQL PostgreSQL instance is set to 'off'
- Ensure 'log_statement_stats' database flag for Cloud SQL PostgreSQL instance is set to 'off'
- Ensure 'log_min_error_statement' database flag for Cloud SQL PostgreSQL instance is set to 'Error' or stricter
- Ensure 'external scripts enabled' database flag for Cloud SQL SQL Server instance is set to 'off'
- Ensure 'user connections' database flag for Cloud SQL SQL Server instance is set as appropriate
- Ensure 'user options' database flag for Cloud SQL SQL Server instance is not configured
- Ensure 'remote access' database flag for Cloud SQL SQL Server instance is set to 'off'
- Ensure '3625 (trace flag)' database flag for Cloud SQL SQL Server instance is set to 'off'
- Ensure that all BigQuery Tables are encrypted with Customer-managed encryption key (CMEK)
- Ensure that a Default Customer-managed encryption key (CMEK) is specified for all BigQuery Data Sets
Security standards contain comprehensive sets of security recommendations to help secure your cloud environments. Security teams can either use the readily available regulatory standards like GCP CIS 1.1.0, GCP CIS 1.2.0 and can also create their own custom standards and assessments to meet specific internal requirements.
It is important to understand, there are three types of resources to create and manage custom assessments:
- Assessment – contains:
a. assessment details (name, description, severity, remediation logic, etc.)
b. assessment logic in KQL
c. the standard it belongs to - Standard – defines a set of assessments
- Standard assignment – defines the scope which the standard will evaluate (e.g. specific GCP account/s)
It is important to understand, there are three types of resources to create and manage custom assessments:
- Assessment – contains:
a. assessment details (name, description, severity, remediation logic, etc.)
b. assessment logic in KQL
c. the standard it belongs to - Standard – defines a set of assessments
- Standard assignment – defines the scope which the standard will evaluate (e.g. specific GCP account/s)
As mentioned, you can either use the built-in regulatory compliance standard or create your own custom standards and assessments.
To assign a built-in regulatory compliance standard or to create and assign a custom standard, follow the steps below:
- Navigate to environment settings
- Select the relevant account
- Select ‘Standards’
- Select ‘Add’ -> ‘Standard’
- Choose a standard from the drop-down menu
- Select ‘Save’
To create a new custom standard:
- Navigate to environment settings
- Select the relevant account
- Select ‘Standards’
- Select ‘Add’ -> ‘Standard’
- Select ‘New standard’
- Fill in a name and description, and select the assessment you want to be included in this standard
- Select ‘Save’
In the screenshot above, you'd notice an additional field "Assessments" which will help you choose from already existing assessments (either built-in or a custom assessment)
Query result Schema
- The last row of the query should return all the original columns (don’t use ‘project’, ‘project-away). End the query with an iff statement that defines the healthy or unhealthy conditions: "| extend HealthStatus = iff([boolean-logic-here], 'UNHEALTHY','HEALTHY')". Check out the example queries below.
Write an assessment query
Examples:
- Ensure that Cloud Storage buckets have uniform bucket-level access enabled
let UnhealthyBuckets = Storage_Bucket
| extend RetentionPolicy = Record.retentionPolicy
| where isnull(RetentionPolicy) or isnull(RetentionPolicy.isLocked) or tobool(RetentionPolicy.isLocked)==false
| project BucketName = RecordIdentifierInfo.CloudNativeResourceName; Logging_LogSink
| extend Destination = split(Record.destination,'/')[0]
| where Destination == 'storage.googleapis.com'
| extend LogBucketName = split(Record.destination,'/')[1]
| extend HealthStatus = iff(LogBucketName in(UnhealthyBuckets), 'UNHEALTHY', 'HEALTHY')"
- Ensure VM disks for critical VMs are encrypted
Compute_Disk
| extend DiskEncryptionKey = Record.diskEncryptionKey
| extend IsVmNotEncrypted = isempty(tostring(DiskEncryptionKey.sha256))
| extend HealthStatus = iff(IsVmNotEncrypted ,'UNHEALTHY' ,'HEALTHY')"
- Ensure Compute instances are launched with Shielded VM enabled
Compute_Instance
| extend InstanceName = tostring(Record.id)
| extend ShieldedVmExist = tostring(Record.shieldedInstanceConfig.enableIntegrityMonitoring) =~ 'true' and tostring(Record.shieldedInstanceConfig.enableVtpm) =~ 'true'
| extend HealthStatus = iff(ShieldedVmExist, 'HEALTHY', 'UNHEALTHY')"
- Ensure KMS encryption keys are rotated within a period of 90 days
CloudKMS_CryptoKey
| extend UnhealthyCryptoKeys = toint(split(Record.rotationPeriod, 's')[0]) > 7776000 or todatetime(Record.nextRotationTime) > now(90d)
| extend HealthStatus = iff(UnhealthyCryptoKeys, 'UNHEALTHY', 'HEALTHY')"
Notes:
- No need to filter records by Timespan. The assessment service will filter the most recent records on each run.
- No need to filter by resource ARN, unless intended. The assessment service will run the query on assigned resources.
- Do not change the values of the original table columns, or use extend to override existing table columns.
- You may use join and union to evaluate a data type based on another type, as long as the evaluated type is the left-hand of the join/union operator and all right-hand columns added by the operator are removed from the result.
- If specific scope is filtered in the assessment query (e.g. specific account Id), it will apply on all resources assigned to this query.
Checkout these useful docs to learn and understand more on Kusto Queries:
- https://docs.microsoft.com/en-us/azure/data-explorer/kql-quick-reference
- https://docs.microsoft.com/en-us/azure/data-explorer/kusto/query/
- https://azurecloudai.blog/2021/11/17/must-learn-kql-part-1-tools-and-resources/
For reference, below is a list of the available data types:
Resource type |
Table name |
BigQuery |
Bigquery_Dataset |
Bigquery_DatasetData |
|
Cloud Key Management |
CloudKMS_CryptoKey |
CloudKMS_CryptoKeyPolicy |
|
CloudKMS_KeyRing |
|
CloudKMS_KeyRingPolicy |
|
Cloud Resource Manager |
CloudResourceManager_Policy |
CloudResourceManager_Project |
|
Compute |
Compute_Disk |
Compute_Firewall |
|
Compute_Instance |
|
Compute_Network |
|
Compute_Project |
|
Compute_SslPolicy |
|
Compute_Subnetwork |
|
Compute_TargetHttpsProxy |
|
Compute_TargetSslProxy |
|
Containers |
Container_Cluster |
DNS |
Dns_ManagedZone |
IAM |
IAM_ServiceAccount |
IAM_ServiceAccountKey |
|
Logging |
Logging_LogMetric |
Logging_LogSink |
|
Monitoring Alert Policy |
Monitoring_AlertPolicy |
SQL |
SQLAdmin_DatabaseInstance |
Storage |
Storage_Bucket |
Storage_BucketPolicy |
Get started today
- Connect your GCP projects to Microsoft Defender for Cloud
- Check out this article for instructions on creating custom assessments and standards in Defender for Cloud for AWS workloads