From 383f11f674479e78b1e39487dc764704bafa4732 Mon Sep 17 00:00:00 2001 From: Andreas Lind Date: Fri, 18 Apr 2025 15:23:20 +0200 Subject: [PATCH v1 4/4] Add bypassleakproof test --- src/test/regress/expected/bypassleakproof.out | 55 +++++++++++++++++++ src/test/regress/parallel_schedule | 2 +- src/test/regress/sql/bypassleakproof.sql | 52 ++++++++++++++++++ 3 files changed, 108 insertions(+), 1 deletion(-) create mode 100644 src/test/regress/expected/bypassleakproof.out create mode 100644 src/test/regress/sql/bypassleakproof.sql diff --git a/src/test/regress/expected/bypassleakproof.out b/src/test/regress/expected/bypassleakproof.out new file mode 100644 index 00000000000..93defc04636 --- /dev/null +++ b/src/test/regress/expected/bypassleakproof.out @@ -0,0 +1,55 @@ +-- BYPASSLEAKPROOF flag +CREATE TYPE foo_or_bar_enum AS ENUM('foo', 'bar'); +CREATE TABLE base_tbl (tenant_id int, foo_or_bar foo_or_bar_enum); +ALTER TABLE base_tbl ENABLE ROW LEVEL SECURITY; +INSERT INTO base_tbl(tenant_id, foo_or_bar) +SELECT 1, 'foo' FROM generate_series(1, 1000) AS n; +INSERT INTO base_tbl(tenant_id, foo_or_bar) +SELECT 2, 'foo' FROM generate_series(1, 1000) AS n; +INSERT INTO base_tbl(tenant_id, foo_or_bar) +VALUES(2, 'bar'); +CREATE FUNCTION is_bar(val foo_or_bar_enum) RETURNS boolean AS $$ SELECT val = 'bar'; $$ LANGUAGE SQL IMMUTABLE; +CREATE INDEX ON base_tbl(tenant_id, (is_bar(foo_or_bar))); +ANALYZE base_tbl; +CREATE USER regress_bypassleakproof_nobypassleakproof_user NOBYPASSLEAKPROOF; +CREATE USER regress_bypassleakproof_bypassleakproof_user BYPASSLEAKPROOF; +GRANT SELECT ON base_tbl TO regress_bypassleakproof_nobypassleakproof_user; +GRANT SELECT ON base_tbl TO regress_bypassleakproof_bypassleakproof_user; +-- Check that the flag gets set correctly: +SELECT rolname, rolbypassleakproof FROM pg_catalog.pg_roles +WHERE rolname LIKE 'regress_bypassleakproof_%' +ORDER BY rolname; + rolname | rolbypassleakproof +------------------------------------------------+-------------------- + regress_bypassleakproof_bypassleakproof_user | t + regress_bypassleakproof_nobypassleakproof_user | f +(2 rows) + +CREATE POLICY only_tenant_2 ON base_tbl FOR ALL +TO regress_bypassleakproof_nobypassleakproof_user, regress_bypassleakproof_bypassleakproof_user +USING (tenant_id = 2); +SET SESSION AUTHORIZATION regress_bypassleakproof_nobypassleakproof_user; +EXPLAIN (verbose, costs off) SELECT * FROM base_tbl WHERE is_bar(foo_or_bar); + QUERY PLAN +----------------------------------------------------------------------------------------- + Seq Scan on public.base_tbl + Output: tenant_id, foo_or_bar + Filter: ((base_tbl.tenant_id = 2) AND (base_tbl.foo_or_bar = 'bar'::foo_or_bar_enum)) +(3 rows) + +RESET SESSION AUTHORIZATION; +SET SESSION AUTHORIZATION regress_bypassleakproof_bypassleakproof_user; +EXPLAIN (verbose, costs off) SELECT * FROM base_tbl WHERE is_bar(foo_or_bar); + QUERY PLAN +------------------------------------------------------------------------------------------------------ + Index Scan using base_tbl_tenant_id_is_bar_idx on public.base_tbl + Output: tenant_id, foo_or_bar + Index Cond: ((base_tbl.tenant_id = 2) AND ((base_tbl.foo_or_bar = 'bar'::foo_or_bar_enum) = true)) +(3 rows) + +RESET SESSION AUTHORIZATION; +DROP TABLE base_tbl CASCADE; +DROP USER regress_bypassleakproof_nobypassleakproof_user; +DROP USER regress_bypassleakproof_bypassleakproof_user; +DROP FUNCTION is_bar; +DROP TYPE foo_or_bar_enum; diff --git a/src/test/regress/parallel_schedule b/src/test/regress/parallel_schedule index 0f38caa0d24..12431a92096 100644 --- a/src/test/regress/parallel_schedule +++ b/src/test/regress/parallel_schedule @@ -43,7 +43,7 @@ test: copy copyselect copydml copyencoding insert insert_conflict # Note: many of the tests in later groups depend on create_index # ---------- test: create_function_c create_misc create_operator create_procedure create_table create_type create_schema -test: create_index create_index_spgist create_view index_including index_including_gist +test: create_index create_index_spgist create_view index_including index_including_gist bypassleakproof # ---------- # Another group of parallel tests diff --git a/src/test/regress/sql/bypassleakproof.sql b/src/test/regress/sql/bypassleakproof.sql new file mode 100644 index 00000000000..2ee42311e91 --- /dev/null +++ b/src/test/regress/sql/bypassleakproof.sql @@ -0,0 +1,52 @@ +-- BYPASSLEAKPROOF flag + +CREATE TYPE foo_or_bar_enum AS ENUM('foo', 'bar'); + +CREATE TABLE base_tbl (tenant_id int, foo_or_bar foo_or_bar_enum); +ALTER TABLE base_tbl ENABLE ROW LEVEL SECURITY; + +INSERT INTO base_tbl(tenant_id, foo_or_bar) +SELECT 1, 'foo' FROM generate_series(1, 1000) AS n; +INSERT INTO base_tbl(tenant_id, foo_or_bar) +SELECT 2, 'foo' FROM generate_series(1, 1000) AS n; +INSERT INTO base_tbl(tenant_id, foo_or_bar) +VALUES(2, 'bar'); + +CREATE FUNCTION is_bar(val foo_or_bar_enum) RETURNS boolean AS $$ SELECT val = 'bar'; $$ LANGUAGE SQL IMMUTABLE; + +CREATE INDEX ON base_tbl(tenant_id, (is_bar(foo_or_bar))); + +ANALYZE base_tbl; + +CREATE USER regress_bypassleakproof_nobypassleakproof_user NOBYPASSLEAKPROOF; +CREATE USER regress_bypassleakproof_bypassleakproof_user BYPASSLEAKPROOF; +GRANT SELECT ON base_tbl TO regress_bypassleakproof_nobypassleakproof_user; +GRANT SELECT ON base_tbl TO regress_bypassleakproof_bypassleakproof_user; + +-- Check that the flag gets set correctly: +SELECT rolname, rolbypassleakproof FROM pg_catalog.pg_roles +WHERE rolname LIKE 'regress_bypassleakproof_%' +ORDER BY rolname; + +CREATE POLICY only_tenant_2 ON base_tbl FOR ALL +TO regress_bypassleakproof_nobypassleakproof_user, regress_bypassleakproof_bypassleakproof_user +USING (tenant_id = 2); + +SET SESSION AUTHORIZATION regress_bypassleakproof_nobypassleakproof_user; + +EXPLAIN (verbose, costs off) SELECT * FROM base_tbl WHERE is_bar(foo_or_bar); + +RESET SESSION AUTHORIZATION; + +SET SESSION AUTHORIZATION regress_bypassleakproof_bypassleakproof_user; + +EXPLAIN (verbose, costs off) SELECT * FROM base_tbl WHERE is_bar(foo_or_bar); + +RESET SESSION AUTHORIZATION; + +DROP TABLE base_tbl CASCADE; + +DROP USER regress_bypassleakproof_nobypassleakproof_user; +DROP USER regress_bypassleakproof_bypassleakproof_user; +DROP FUNCTION is_bar; +DROP TYPE foo_or_bar_enum; -- 2.39.2