1730 lines
58 KiB
Diff
1730 lines
58 KiB
Diff
diff -rpNU3 base/src/test/regress/expected/sanity_check.out sepgsql-new/src/test/regress/expected/sanity_check.out
|
|
--- base/src/test/regress/expected/sanity_check.out 2007-11-25 12:49:12.000000000 +0900
|
|
+++ sepgsql-new/src/test/regress/expected/sanity_check.out 2009-03-13 18:14:33.000000000 +0900
|
|
@@ -111,6 +111,7 @@ SELECT relname, relhasindex
|
|
pg_pltemplate | t
|
|
pg_proc | t
|
|
pg_rewrite | t
|
|
+ pg_security | t
|
|
pg_shdepend | t
|
|
pg_shdescription | t
|
|
pg_statistic | t
|
|
@@ -149,7 +150,7 @@ SELECT relname, relhasindex
|
|
timetz_tbl | f
|
|
tinterval_tbl | f
|
|
varchar_tbl | f
|
|
-(138 rows)
|
|
+(139 rows)
|
|
|
|
--
|
|
-- another sanity check: every system catalog that has OIDs should have
|
|
diff -rpNU3 base/src/test/sepgsql/Makefile sepgsql-new/src/test/sepgsql/Makefile
|
|
--- base/src/test/sepgsql/Makefile 1970-01-01 09:00:00.000000000 +0900
|
|
+++ sepgsql-new/src/test/sepgsql/Makefile 2009-03-03 18:21:14.000000000 +0900
|
|
@@ -0,0 +1,65 @@
|
|
+# ----------------------------------------------------
|
|
+# Makefile for SE-PostgreSQL testcases
|
|
+# ----------------------------------------------------
|
|
+PSQL := $(shell which psql)
|
|
+DIFF := $(shell which diff)
|
|
+RUNCON := $(shell which runcon)
|
|
+GETSEBOOL := $(shell which getsebool)
|
|
+DBNAME := test
|
|
+
|
|
+TESTCASES = $(wildcard sql/*.sql)
|
|
+
|
|
+test: init check setup results.diff
|
|
+
|
|
+init:
|
|
+ rm -f results.diff results/*.out results/*.diff
|
|
+
|
|
+clean: init
|
|
+ rm -f launch_psql
|
|
+
|
|
+launch_psql: launch_psql.c
|
|
+ $(CC) $< -o $@ -lselinux
|
|
+
|
|
+results.diff: $(TESTCASES:sql/%.sql=results/%.diff)
|
|
+ @for x in $^; do cat $$x >> $@; done
|
|
+ @test -s $@ && echo "HINT: See $@ to confirm errors" || :
|
|
+
|
|
+results/%.diff: sql/%.sql
|
|
+ @./launch_psql $(PSQL) -a $(DBNAME) < $< >& $(@:%.diff=%.out)
|
|
+ @$(DIFF) -u $(<:sql/%.sql=expected/%.out) \
|
|
+ $(<:sql/%.sql=results/%.out) >& $@ \
|
|
+ && echo -n "PASS: " || echo -n "FAIL: "
|
|
+ @echo $(notdir $(@:.diff=))
|
|
+
|
|
+setup: launch_psql
|
|
+ @cp -f /dev/null /tmp/sepgsql_test_copy_1
|
|
+ @cp -f /dev/null /tmp/sepgsql_test_copy_2
|
|
+ @chcon -t postgresql_tmp_t -l s0 /tmp/sepgsql_test_copy_1
|
|
+ @chcon -t postgresql_db_t -l s0 /tmp/sepgsql_test_copy_2
|
|
+ @dd if=/dev/zero of=/tmp/sepgsql_test_blob1 bs=1024 count=20 >& /dev/null
|
|
+ @dd if=/dev/zero of=/tmp/sepgsql_test_blob2 bs=1024 count=20 >& /dev/null
|
|
+ @chcon -t postgresql_tmp_t -l s0 /tmp/sepgsql_test_blob1
|
|
+ @chcon -t postgresql_db_t -l s0 /tmp/sepgsql_test_blob2
|
|
+ @chmod 0666 /tmp/sepgsql_test_*
|
|
+ @echo "PASS: setup filesystem objects"
|
|
+
|
|
+check:
|
|
+ @test -x $(PSQL) || \
|
|
+ (echo "HINT: $(PSQL) is not available"; exit 1)
|
|
+ @$(PSQL) -qt -c 'SHOW sepostgresql' -d $(DBNAME) 2>/dev/null | grep -q on || \
|
|
+ (echo "HINT: database \"$(DBNAME)\" is not available"; \
|
|
+ echo "HINT: SE-PostgreSQL may not be available on server"; exit 1)
|
|
+ @$(GETSEBOOL) allow_user_postgresql_connect | grep -q on || \
|
|
+ (echo "HINT: check allow_user_postgresql_connect boolean"; exit 1)
|
|
+ @$(GETSEBOOL) sepgsql_regression_test_mode | grep -q on || \
|
|
+ (echo "HINT: check sepgsql_regression_test_mode boolean"; \
|
|
+ echo "HINT: check sepostgresql-devel.pp installed"; exit 1)
|
|
+ @$(RUNCON) -t sepgsql_test_t -l s0-s0:c0.c15 \
|
|
+ $(PSQL) -c 'SELECT sepgsql_getcon()' $(DBNAME) >& /dev/null || \
|
|
+ (echo "HINT: /sbin/restorecon -R <prefix> and restart"; \
|
|
+ echo "HINT: user shell should have 's0-s0:c0.c15' range, at least"; \
|
|
+ echo " semanage enables to set up it"; exit 1)
|
|
+ @test -x /etc/init.d/mcstrans && /etc/init.d/mcstrans status >& /dev/null && \
|
|
+ (echo "HINT: stop mcstrans daemon"; exit 1) || \
|
|
+ (test $$? -eq 3 && exit 0 || exit 1)
|
|
+ @echo "PASS: check runtime environment"
|
|
diff -rpNU3 base/src/test/sepgsql/expected/basic.out sepgsql-new/src/test/sepgsql/expected/basic.out
|
|
--- base/src/test/sepgsql/expected/basic.out 1970-01-01 09:00:00.000000000 +0900
|
|
+++ sepgsql-new/src/test/sepgsql/expected/basic.out 2009-03-15 17:38:39.000000000 +0900
|
|
@@ -0,0 +1,108 @@
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+SELECT sepgsql_getcon();
|
|
+ sepgsql_getcon
|
|
+-----------------------------------------------------
|
|
+ unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+(1 row)
|
|
+
|
|
+-- cleanup previous tests
|
|
+SET client_min_messages TO 'error';
|
|
+SET
|
|
+DROP TABLE IF EXISTS t4 CASCADE;
|
|
+DROP TABLE
|
|
+DROP TABLE IF EXISTS t3 CASCADE;
|
|
+DROP TABLE
|
|
+DROP TABLE IF EXISTS t2 CASCADE;
|
|
+DROP TABLE
|
|
+DROP TABLE IF EXISTS t1 CASCADE;
|
|
+DROP TABLE
|
|
+DROP FUNCTION IF EXISTS f1(int) CASCADE;
|
|
+DROP FUNCTION
|
|
+RESET client_min_messages;
|
|
+RESET
|
|
+-- SETUP
|
|
+CREATE TABLE t1
|
|
+(
|
|
+ a int,
|
|
+ b text
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_ro_table_t:s0',
|
|
+ c bool
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_secret_table_t:s0'
|
|
+);
|
|
+CREATE TABLE
|
|
+INSERT INTO t1 VALUES (1, 'aaa', false), (2, 'bbb', true);
|
|
+INSERT 0 2
|
|
+CREATE TABLE t2
|
|
+(
|
|
+ s int,
|
|
+ t int,
|
|
+ u int
|
|
+) SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_table_t:s0:c0';
|
|
+CREATE TABLE
|
|
+ALTER TABLE t2 DROP COLUMN t; -- disturbing factor
|
|
+ALTER TABLE
|
|
+CREATE TABLE t3
|
|
+(
|
|
+ x text
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_table_t:s0:c1'
|
|
+) inherits(t2);
|
|
+CREATE TABLE
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0
|
|
+SELECT sepgsql_getcon();
|
|
+ sepgsql_getcon
|
|
+---------------------------------------------------
|
|
+ unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0
|
|
+(1 row)
|
|
+
|
|
+SELECT * FROM t1; -- to be denied
|
|
+ERROR: SELinux: denied { select } scontext=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0 tcontext=unconfined_u:object_r:sepgsql_secret_table_t:s0 tclass=db_column name=t1.c
|
|
+SELECT a, b FROM t1;
|
|
+ a | b
|
|
+---+-----
|
|
+ 1 | aaa
|
|
+ 2 | bbb
|
|
+(2 rows)
|
|
+
|
|
+SELECT COUNT(*) FROM t1 WHERE c; -- to be denied
|
|
+ERROR: SELinux: denied { select } scontext=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0 tcontext=unconfined_u:object_r:sepgsql_secret_table_t:s0 tclass=db_column name=t1.c
|
|
+UPDATE t1 SET b = 'ccc'; -- to be denied
|
|
+ERROR: SELinux: denied { update } scontext=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0 tcontext=unconfined_u:object_r:sepgsql_ro_table_t:s0 tclass=db_column name=t1.b
|
|
+UPDATE t1 SET a = a + 2;
|
|
+UPDATE 2
|
|
+INSERT INTO t1 VALUES (5, 'eee', true); -- to be denied
|
|
+ERROR: SELinux: denied { insert } scontext=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0 tcontext=unconfined_u:object_r:sepgsql_ro_table_t:s0 tclass=db_column name=t1.b
|
|
+INSERT INTO t1 VALUES (5);
|
|
+INSERT 0 1
|
|
+SELECT * FROM t2;
|
|
+ s | u
|
|
+---+---
|
|
+(0 rows)
|
|
+
|
|
+SELECT t2 FROM t2;
|
|
+ t2
|
|
+----
|
|
+(0 rows)
|
|
+
|
|
+SELECT t3 FROM t3; -- to be denied
|
|
+ERROR: SELinux: denied { select } scontext=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0 tcontext=unconfined_u:object_r:sepgsql_table_t:s0:c1 tclass=db_column name=t3.x
|
|
+SELECT 1 FROM t3;
|
|
+ ?column?
|
|
+----------
|
|
+(0 rows)
|
|
+
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c1
|
|
+SELECT sepgsql_getcon();
|
|
+ sepgsql_getcon
|
|
+---------------------------------------------------
|
|
+ unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c1
|
|
+(1 row)
|
|
+
|
|
+SELECT * FROM t2; -- to be denied
|
|
+ERROR: SELinux: denied { select } scontext=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c1 tcontext=unconfined_u:object_r:sepgsql_table_t:s0:c0 tclass=db_table name=t2
|
|
+SELECT t2 FROM t2; -- to be denied
|
|
+ERROR: SELinux: denied { select } scontext=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c1 tcontext=unconfined_u:object_r:sepgsql_table_t:s0:c0 tclass=db_table name=t2
|
|
+SELECT t3 FROM t3;
|
|
+ t3
|
|
+----
|
|
+(0 rows)
|
|
+
|
|
diff -rpNU3 base/src/test/sepgsql/expected/copy_stmt.out sepgsql-new/src/test/sepgsql/expected/copy_stmt.out
|
|
--- base/src/test/sepgsql/expected/copy_stmt.out 1970-01-01 09:00:00.000000000 +0900
|
|
+++ sepgsql-new/src/test/sepgsql/expected/copy_stmt.out 2009-03-02 00:24:34.000000000 +0900
|
|
@@ -0,0 +1,90 @@
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+SELECT sepgsql_getcon();
|
|
+ sepgsql_getcon
|
|
+-----------------------------------------------------
|
|
+ unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+(1 row)
|
|
+
|
|
+-- cleanup previous tests
|
|
+SET client_min_messages TO 'error';
|
|
+SET
|
|
+DROP TABLE IF EXISTS t3 CASCADE;
|
|
+DROP TABLE
|
|
+DROP TABLE IF EXISTS t2 CASCADE;
|
|
+DROP TABLE
|
|
+DROP TABLE IF EXISTS t1 CASCADE;
|
|
+DROP TABLE
|
|
+DROP FUNCTION IF EXISTS f1(int) CASCADE;
|
|
+DROP FUNCTION
|
|
+RESET client_min_messages;
|
|
+RESET
|
|
+-- setup tables
|
|
+CREATE TABLE t1
|
|
+(
|
|
+ a int,
|
|
+ b text
|
|
+);
|
|
+CREATE TABLE
|
|
+INSERT INTO t1 VALUES (1, 'aaa'), (2, 'bbb');
|
|
+INSERT 0 2
|
|
+CREATE TABLE t2
|
|
+(
|
|
+ x int,
|
|
+ y text
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_secret_table_t:s0'
|
|
+);
|
|
+CREATE TABLE
|
|
+SELECT security_context from pg_attribute where attrelid = 't2'::regclass and attname = 'y';
|
|
+ security_context
|
|
+-------------------------------------------------
|
|
+ unconfined_u:object_r:sepgsql_secret_table_t:s0
|
|
+(1 row)
|
|
+
|
|
+INSERT INTO t2 VALUES (1, 'xxx'), (2, 'yyy');
|
|
+INSERT 0 2
|
|
+CREATE TABLE t3 -- read only table
|
|
+(
|
|
+ s int,
|
|
+ t text
|
|
+) SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_ro_table_t:s0';
|
|
+CREATE TABLE
|
|
+INSERT INTO t2 VALUES (1, 'sss'), (2, 'ttt');
|
|
+INSERT 0 2
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0
|
|
+SELECT sepgsql_getcon();
|
|
+ sepgsql_getcon
|
|
+---------------------------------------------------
|
|
+ unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0
|
|
+(1 row)
|
|
+
|
|
+COPY t1 TO stdout;
|
|
+1 aaa
|
|
+2 bbb
|
|
+COPY t1 FROM stdin;
|
|
+COPY t1 TO '/tmp/sepgsql_test_copy_1';
|
|
+COPY 4
|
|
+COPY t1 TO '/tmp/sepgsql_test_copy_2'; -- to be denied
|
|
+ERROR: SELinux: denied { write } scontext=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0 tcontext=unconfined_u:object_r:postgresql_db_t:s0 tclass=file name=/tmp/sepgsql_test_copy_2
|
|
+COPY t2 TO stdout; -- to be denied
|
|
+ERROR: SELinux: denied { select } scontext=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0 tcontext=unconfined_u:object_r:sepgsql_secret_table_t:s0 tclass=db_column name=t2.y
|
|
+COPY t2 FROM stdin; -- to be denied
|
|
+ERROR: SELinux: denied { insert } scontext=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0 tcontext=unconfined_u:object_r:sepgsql_secret_table_t:s0 tclass=db_column name=t2.y
|
|
+COPY t2 (x) TO stdout;
|
|
+1
|
|
+2
|
|
+1
|
|
+2
|
|
+COPY t3 TO stdout;
|
|
+COPY t3 FROM '/tmp/sepgsql_test_copy_1'; -- to be denied
|
|
+ERROR: SELinux: denied { insert } scontext=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0 tcontext=unconfined_u:object_r:sepgsql_ro_table_t:s0 tclass=db_table name=t3
|
|
+COPY t1 FROM '/tmp/sepgsql_test_copy_1';
|
|
+COPY 4
|
|
+COPY t1 TO stdout;
|
|
+1 aaa
|
|
+2 bbb
|
|
+3 ccc
|
|
+4 ddd
|
|
+1 aaa
|
|
+2 bbb
|
|
+3 ccc
|
|
+4 ddd
|
|
diff -rpNU3 base/src/test/sepgsql/expected/enhanced_ddl_stmt.out sepgsql-new/src/test/sepgsql/expected/enhanced_ddl_stmt.out
|
|
--- base/src/test/sepgsql/expected/enhanced_ddl_stmt.out 1970-01-01 09:00:00.000000000 +0900
|
|
+++ sepgsql-new/src/test/sepgsql/expected/enhanced_ddl_stmt.out 2009-03-15 17:38:39.000000000 +0900
|
|
@@ -0,0 +1,180 @@
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+SELECT sepgsql_getcon();
|
|
+ sepgsql_getcon
|
|
+-----------------------------------------------------
|
|
+ unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+(1 row)
|
|
+
|
|
+-- cleanup previous tests
|
|
+SET client_min_messages TO 'error';
|
|
+SET
|
|
+DROP TABLE IF EXISTS t4 CASCADE;
|
|
+DROP TABLE
|
|
+DROP TABLE IF EXISTS t3 CASCADE;
|
|
+DROP TABLE
|
|
+DROP TABLE IF EXISTS t2 CASCADE;
|
|
+DROP TABLE
|
|
+DROP TABLE IF EXISTS t1 CASCADE;
|
|
+DROP TABLE
|
|
+DROP FUNCTION IF EXISTS f1(int) CASCADE;
|
|
+DROP FUNCTION
|
|
+DROP FUNCTION IF EXISTS f2(int) CASCADE;
|
|
+DROP FUNCTION
|
|
+RESET client_min_messages;
|
|
+RESET
|
|
+-- CREATE TABLE with SECURITY_LABEL clause
|
|
+CREATE TABLE t1 (
|
|
+ a int,
|
|
+ b text
|
|
+);
|
|
+CREATE TABLE
|
|
+SELECT relname, security_context FROM pg_class WHERE oid = 't1'::regclass;
|
|
+ relname | security_context
|
|
+---------+------------------------------------------
|
|
+ t1 | unconfined_u:object_r:sepgsql_table_t:s0
|
|
+(1 row)
|
|
+
|
|
+SELECT attname, security_context FROM pg_attribute WHERE attrelid = 't1'::regclass and attnum > 0;
|
|
+ attname | security_context
|
|
+---------+------------------------------------------
|
|
+ a | unconfined_u:object_r:sepgsql_table_t:s0
|
|
+ b | unconfined_u:object_r:sepgsql_table_t:s0
|
|
+(2 rows)
|
|
+
|
|
+CREATE TABLE t2 (
|
|
+ a int,
|
|
+ b text
|
|
+) SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_ro_table_t:s0';
|
|
+CREATE TABLE
|
|
+SELECT relname, security_context FROM pg_class WHERE oid = 't2'::regclass;
|
|
+ relname | security_context
|
|
+---------+---------------------------------------------
|
|
+ t2 | unconfined_u:object_r:sepgsql_ro_table_t:s0
|
|
+(1 row)
|
|
+
|
|
+SELECT attname, security_context FROM pg_attribute WHERE attrelid = 't2'::regclass and attnum > 0;
|
|
+ attname | security_context
|
|
+---------+---------------------------------------------
|
|
+ a | unconfined_u:object_r:sepgsql_ro_table_t:s0
|
|
+ b | unconfined_u:object_r:sepgsql_ro_table_t:s0
|
|
+(2 rows)
|
|
+
|
|
+CREATE TABLE t3 (
|
|
+ a int,
|
|
+ b text SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_fixed_table_t:s0',
|
|
+ c bool SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_secret_table_t:s0',
|
|
+ d int
|
|
+) SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_table_t:s0:c0';
|
|
+CREATE TABLE
|
|
+SELECT relname, security_context FROM pg_class WHERE oid = 't3'::regclass;
|
|
+ relname | security_context
|
|
+---------+---------------------------------------------
|
|
+ t3 | unconfined_u:object_r:sepgsql_table_t:s0:c0
|
|
+(1 row)
|
|
+
|
|
+SELECT attname, security_context FROM pg_attribute WHERE attrelid = 't3'::regclass and attnum > 0;
|
|
+ attname | security_context
|
|
+---------+-------------------------------------------------
|
|
+ a | unconfined_u:object_r:sepgsql_table_t:s0
|
|
+ b | unconfined_u:object_r:sepgsql_fixed_table_t:s0
|
|
+ c | unconfined_u:object_r:sepgsql_secret_table_t:s0
|
|
+ d | unconfined_u:object_r:sepgsql_table_t:s0
|
|
+(4 rows)
|
|
+
|
|
+CREATE TABLE t4 (
|
|
+ a int,
|
|
+ b text
|
|
+) SECURITY_CONTEXT = 'unconfined_u:object_r:invalid_label_t:s0'; -- to be failed
|
|
+ERROR: invalid security label: unconfined_u:object_r:invalid_label_t:s0
|
|
+CREATE TABLE t4 (
|
|
+ a int,
|
|
+ b text
|
|
+) SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_proc_t:s0'; -- to be denied
|
|
+ERROR: SELinux: denied { create } scontext=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15 tcontext=unconfined_u:object_r:sepgsql_proc_t:s0 tclass=db_table name=t4
|
|
+-- ALTER TABLE with SECURITY_CONTEXT clause
|
|
+ALTER TABLE t2 SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_secret_table_t:s0';
|
|
+ALTER TABLE
|
|
+ALTER TABLE t2 ADD COLUMN c bool; -- it inherits table's one
|
|
+ALTER TABLE
|
|
+SELECT relname, security_context FROM pg_class WHERE oid = 't2'::regclass;
|
|
+ relname | security_context
|
|
+---------+-------------------------------------------------
|
|
+ t2 | unconfined_u:object_r:sepgsql_secret_table_t:s0
|
|
+(1 row)
|
|
+
|
|
+SELECT attname, security_context FROM pg_attribute WHERE attrelid = 't2'::regclass and attnum > 0;
|
|
+ attname | security_context
|
|
+---------+-------------------------------------------------
|
|
+ a | unconfined_u:object_r:sepgsql_ro_table_t:s0
|
|
+ b | unconfined_u:object_r:sepgsql_ro_table_t:s0
|
|
+ c | unconfined_u:object_r:sepgsql_secret_table_t:s0
|
|
+(3 rows)
|
|
+
|
|
+ALTER TABLE t3 ALTER b SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_table_t:s0';
|
|
+ALTER TABLE
|
|
+SELECT relname, security_context FROM pg_class WHERE oid = 't3'::regclass;
|
|
+ relname | security_context
|
|
+---------+---------------------------------------------
|
|
+ t3 | unconfined_u:object_r:sepgsql_table_t:s0:c0
|
|
+(1 row)
|
|
+
|
|
+SELECT attname, security_context FROM pg_attribute WHERE attrelid = 't3'::regclass and attnum > 0;
|
|
+ attname | security_context
|
|
+---------+-------------------------------------------------
|
|
+ a | unconfined_u:object_r:sepgsql_table_t:s0
|
|
+ b | unconfined_u:object_r:sepgsql_table_t:s0
|
|
+ c | unconfined_u:object_r:sepgsql_secret_table_t:s0
|
|
+ d | unconfined_u:object_r:sepgsql_table_t:s0
|
|
+(4 rows)
|
|
+
|
|
+-- CREATE FUNCTION with SECURITY_CONTEXT clause
|
|
+CREATE FUNCTION f1 (int) RETURNS int
|
|
+ LANGUAGE 'sql'
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_proc_t:s0:c0'
|
|
+ AS 'SELECT $1 * 2';
|
|
+CREATE FUNCTION
|
|
+SELECT proname, security_context FROM pg_proc WHERE oid = 'f1'::regproc;
|
|
+ proname | security_context
|
|
+---------+--------------------------------------------
|
|
+ f1 | unconfined_u:object_r:sepgsql_proc_t:s0:c0
|
|
+(1 row)
|
|
+
|
|
+CREATE FUNCTION f2 (int) RETURNS int
|
|
+ LANGUAGE 'sql'
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:invalid_label_t:s0'
|
|
+ AS 'SELECT $1 + $1'; -- to be failed
|
|
+ERROR: invalid security label: unconfined_u:object_r:invalid_label_t:s0
|
|
+CREATE FUNCTION f2 (int) RETURNS int
|
|
+ LANGUAGE 'sql'
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_proc_t:s0:c16'
|
|
+ AS 'SELECT $1 + $1'; -- to be denied
|
|
+ERROR: SELinux: denied { create } scontext=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15 tcontext=unconfined_u:object_r:sepgsql_proc_t:s0:c16 tclass=db_procedure name=f2
|
|
+CREATE FUNCTION f2 (int) RETURNS int
|
|
+ LANGUAGE 'sql'
|
|
+ AS 'SELECT $1 + $1';
|
|
+CREATE FUNCTION
|
|
+SELECT proname, security_context FROM pg_proc WHERE oid = 'f2'::regproc;
|
|
+ proname | security_context
|
|
+---------+-----------------------------------------
|
|
+ f2 | unconfined_u:object_r:sepgsql_proc_t:s0
|
|
+(1 row)
|
|
+
|
|
+-- ALTER FUNCTION with SECURITY_CONTEXT clause
|
|
+ALTER FUNCTION f1(int)
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_proc_t:s0:c1';
|
|
+ALTER FUNCTION
|
|
+SELECT proname, security_context FROM pg_proc WHERE oid = 'f1'::regproc;
|
|
+ proname | security_context
|
|
+---------+--------------------------------------------
|
|
+ f1 | unconfined_u:object_r:sepgsql_proc_t:s0:c1
|
|
+(1 row)
|
|
+
|
|
+ALTER FUNCTION f2(int)
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_proc_t:s0:c16'; -- to be denied
|
|
+ERROR: SELinux: denied { relabelto } scontext=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15 tcontext=unconfined_u:object_r:sepgsql_proc_t:s0:c16 tclass=db_procedure name=f2
|
|
+SELECT proname, security_context FROM pg_proc WHERE oid = 'f2'::regproc;
|
|
+ proname | security_context
|
|
+---------+-----------------------------------------
|
|
+ f2 | unconfined_u:object_r:sepgsql_proc_t:s0
|
|
+(1 row)
|
|
+
|
|
diff -rpNU3 base/src/test/sepgsql/expected/join_query.out sepgsql-new/src/test/sepgsql/expected/join_query.out
|
|
--- base/src/test/sepgsql/expected/join_query.out 1970-01-01 09:00:00.000000000 +0900
|
|
+++ sepgsql-new/src/test/sepgsql/expected/join_query.out 2009-03-15 17:38:39.000000000 +0900
|
|
@@ -0,0 +1,85 @@
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+SELECT sepgsql_getcon();
|
|
+ sepgsql_getcon
|
|
+-----------------------------------------------------
|
|
+ unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+(1 row)
|
|
+
|
|
+-- cleanup previous tests
|
|
+SET client_min_messages TO 'error';
|
|
+SET
|
|
+DROP TABLE IF EXISTS t4 CASCADE;
|
|
+DROP TABLE
|
|
+DROP TABLE IF EXISTS t3 CASCADE;
|
|
+DROP TABLE
|
|
+DROP TABLE IF EXISTS t2 CASCADE;
|
|
+DROP TABLE
|
|
+DROP TABLE IF EXISTS t1 CASCADE;
|
|
+DROP TABLE
|
|
+DROP FUNCTION IF EXISTS f1(int) CASCADE;
|
|
+DROP FUNCTION
|
|
+RESET client_min_messages;
|
|
+RESET
|
|
+-- SETUP
|
|
+CREATE TABLE t1
|
|
+(
|
|
+ a int,
|
|
+ b text,
|
|
+ c int
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_secret_table_t:s0'
|
|
+);
|
|
+CREATE TABLE
|
|
+INSERT INTO t1 VALUES (1, 'aaa'), (2, 'bbb'), (3, 'ccc');
|
|
+INSERT 0 3
|
|
+CREATE TABLE t2
|
|
+(
|
|
+ x int,
|
|
+ y text
|
|
+);
|
|
+CREATE TABLE
|
|
+INSERT INTO t2 VALUES (2, 'xxx'), (3, 'yyy'), (4,'zzz');
|
|
+INSERT 0 3
|
|
+CREATE TABLE t3
|
|
+(
|
|
+ d int
|
|
+) INHERITS (t1);
|
|
+CREATE TABLE
|
|
+INSERT INTO t3 VALUES (4, 'ddd'), (5, 'eee');
|
|
+INSERT 0 2
|
|
+CREATE TABLE t4
|
|
+(
|
|
+ z int
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_secret_table_t:s0'
|
|
+) INHERITS (t2);
|
|
+CREATE TABLE
|
|
+INSERT INTO t2 VALUES (1, 'sss'), (5, 'ttt');
|
|
+INSERT 0 2
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0
|
|
+SELECT sepgsql_getcon();
|
|
+ sepgsql_getcon
|
|
+---------------------------------------------------
|
|
+ unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0
|
|
+(1 row)
|
|
+
|
|
+SELECT * FROM t1 JOIN t2 ON a = x; -- to be denied
|
|
+ERROR: SELinux: denied { select } scontext=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0 tcontext=unconfined_u:object_r:sepgsql_secret_table_t:s0 tclass=db_column name=t1.c
|
|
+SELECT a, b, y FROM t1 JOIN t2 ON a = x;
|
|
+ a | b | y
|
|
+---+-----+-----
|
|
+ 1 | aaa | sss
|
|
+ 2 | bbb | xxx
|
|
+ 3 | ccc | yyy
|
|
+ 4 | ddd | zzz
|
|
+ 5 | eee | ttt
|
|
+(5 rows)
|
|
+
|
|
+SELECT a, b, y FROM t1 JOIN t2 ON c = x; -- to be denied
|
|
+ERROR: SELinux: denied { select } scontext=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0 tcontext=unconfined_u:object_r:sepgsql_secret_table_t:s0 tclass=db_column name=t1.c
|
|
+SELECT COUNT(*) FROM t1 JOIN t2 ON a = x;
|
|
+ count
|
|
+-------
|
|
+ 5
|
|
+(1 row)
|
|
+
|
|
+SELECT j FROM (t1 JOIN t2 ON a = x) AS j; -- to be denied
|
|
+ERROR: SELinux: denied { select } scontext=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0 tcontext=unconfined_u:object_r:sepgsql_secret_table_t:s0 tclass=db_column name=t1.c
|
|
diff -rpNU3 base/src/test/sepgsql/expected/large_object.out sepgsql-new/src/test/sepgsql/expected/large_object.out
|
|
--- base/src/test/sepgsql/expected/large_object.out 1970-01-01 09:00:00.000000000 +0900
|
|
+++ sepgsql-new/src/test/sepgsql/expected/large_object.out 2009-03-03 14:31:40.000000000 +0900
|
|
@@ -0,0 +1,293 @@
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+SELECT sepgsql_getcon();
|
|
+ sepgsql_getcon
|
|
+-----------------------------------------------------
|
|
+ unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+(1 row)
|
|
+
|
|
+-- cleanup previous tests
|
|
+SET client_min_messages TO 'error';
|
|
+SET
|
|
+DROP TABLE IF EXISTS lolabel CASCADE;
|
|
+DROP TABLE
|
|
+DROP FUNCTION IF EXISTS lo_label(oid) CASCADE;
|
|
+DROP FUNCTION
|
|
+RESET client_min_messages;
|
|
+RESET
|
|
+CREATE TABLE lolabel(
|
|
+ loid oid,
|
|
+ label text
|
|
+);
|
|
+CREATE TABLE
|
|
+CREATE OR REPLACE FUNCTION lo_label(oid)
|
|
+ RETURNS TEXT LANGUAGE 'sql'
|
|
+ AS 'SELECT label FROM lolabel WHERE loid = $1';
|
|
+CREATE FUNCTION
|
|
+INSERT INTO lolabel (SELECT lo_import('/tmp/sepgsql_test_blob1'), 'normal');
|
|
+INSERT 0 1
|
|
+INSERT INTO lolabel (SELECT lo_import('/tmp/sepgsql_test_blob1'), 'readonly');
|
|
+INSERT 0 1
|
|
+INSERT INTO lolabel (SELECT lo_import('/tmp/sepgsql_test_blob1'), 'secret');
|
|
+INSERT 0 1
|
|
+SELECT lo_set_security(loid, 'system_u:object_r:sepgsql_blob_t:s0')
|
|
+ FROM lolabel WHERE label = 'normal';
|
|
+ lo_set_security
|
|
+-----------------
|
|
+ t
|
|
+(1 row)
|
|
+
|
|
+SELECT lo_set_security(loid, 'system_u:object_r:sepgsql_ro_blob_t:s0')
|
|
+ FROM lolabel WHERE label = 'readonly';
|
|
+ lo_set_security
|
|
+-----------------
|
|
+ t
|
|
+(1 row)
|
|
+
|
|
+SELECT lo_set_security(loid, 'system_u:object_r:sepgsql_secret_blob_t:s0')
|
|
+ FROM lolabel WHERE label = 'secret';
|
|
+ lo_set_security
|
|
+-----------------
|
|
+ t
|
|
+(1 row)
|
|
+
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:sepgsql_test_t:s0:c0
|
|
+SELECT sepgsql_getcon();
|
|
+ sepgsql_getcon
|
|
+------------------------------------------------
|
|
+ unconfined_u:unconfined_r:sepgsql_test_t:s0:c0
|
|
+(1 row)
|
|
+
|
|
+SELECT lo_get_security(loid) FROM lolabel;
|
|
+ lo_get_security
|
|
+--------------------------------------------
|
|
+ system_u:object_r:sepgsql_blob_t:s0
|
|
+ system_u:object_r:sepgsql_ro_blob_t:s0
|
|
+ system_u:object_r:sepgsql_secret_blob_t:s0
|
|
+(3 rows)
|
|
+
|
|
+SELECT security_context, lo_label(loid) AS label, COUNT(*)
|
|
+ FROM pg_largeobject GROUP BY security_context, loid ORDER by label;
|
|
+ security_context | label | count
|
|
+--------------------------------------------+----------+-------
|
|
+ system_u:object_r:sepgsql_blob_t:s0 | normal | 10
|
|
+ system_u:object_r:sepgsql_ro_blob_t:s0 | readonly | 10
|
|
+ system_u:object_r:sepgsql_secret_blob_t:s0 | secret | 10
|
|
+(3 rows)
|
|
+
|
|
+-- read large object
|
|
+BEGIN;
|
|
+BEGIN
|
|
+SELECT lo_open(loid, x'40000'::int) FROM lolabel WHERE label = 'normal';
|
|
+ lo_open
|
|
+---------
|
|
+ 0
|
|
+(1 row)
|
|
+
|
|
+SELECT loread(0, 32);
|
|
+ loread
|
|
+----------------------------------------------------------------------------------------------------------------------------------
|
|
+ \000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000
|
|
+(1 row)
|
|
+
|
|
+ROLLBACK;
|
|
+ROLLBACK
|
|
+BEGIN;
|
|
+BEGIN
|
|
+SELECT lo_open(loid, x'40000'::int) FROM lolabel WHERE label = 'readonly';
|
|
+ lo_open
|
|
+---------
|
|
+ 0
|
|
+(1 row)
|
|
+
|
|
+SELECT loread(0, 32);
|
|
+ loread
|
|
+----------------------------------------------------------------------------------------------------------------------------------
|
|
+ \000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000
|
|
+(1 row)
|
|
+
|
|
+ROLLBACK;
|
|
+ROLLBACK
|
|
+BEGIN;
|
|
+BEGIN
|
|
+SELECT lo_open(loid, x'40000'::int) FROM lolabel WHERE label = 'secret';
|
|
+ lo_open
|
|
+---------
|
|
+ 0
|
|
+(1 row)
|
|
+
|
|
+SELECT loread(0, 32); -- to be denied
|
|
+ERROR: SELinux: security policy violation
|
|
+ROLLBACK;
|
|
+ROLLBACK
|
|
+-- write large object
|
|
+BEGIN;
|
|
+BEGIN
|
|
+SELECT lo_open(loid, x'20000'::int) FROM lolabel WHERE label = 'normal';
|
|
+ lo_open
|
|
+---------
|
|
+ 0
|
|
+(1 row)
|
|
+
|
|
+SELECT lowrite(0, 'ABCDEFGHIJKLMNOPQRSTUVWXYZ');
|
|
+ lowrite
|
|
+---------
|
|
+ 26
|
|
+(1 row)
|
|
+
|
|
+ROLLBACK;
|
|
+ROLLBACK
|
|
+BEGIN;
|
|
+BEGIN
|
|
+SELECT lo_open(loid, x'20000'::int) FROM lolabel WHERE label = 'readonly';
|
|
+ lo_open
|
|
+---------
|
|
+ 0
|
|
+(1 row)
|
|
+
|
|
+SELECT lowrite(0, 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'); -- to be denied
|
|
+ERROR: SELinux: security policy violation
|
|
+ROLLBACK;
|
|
+ROLLBACK
|
|
+BEGIN;
|
|
+BEGIN
|
|
+SELECT lo_open(loid, x'20000'::int) FROM lolabel WHERE label = 'secret';
|
|
+ lo_open
|
|
+---------
|
|
+ 0
|
|
+(1 row)
|
|
+
|
|
+SELECT lowrite(0, 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'); -- to be denied
|
|
+ERROR: SELinux: security policy violation
|
|
+ROLLBACK;
|
|
+ROLLBACK
|
|
+-- create large object
|
|
+BEGIN;
|
|
+BEGIN
|
|
+INSERT INTO lolabel (SELECT lo_create(6004), 'local');
|
|
+INSERT 0 1
|
|
+SELECT lo_open(loid, x'20000'::int) FROM lolabel WHERE label = 'local';
|
|
+ lo_open
|
|
+---------
|
|
+ 0
|
|
+(1 row)
|
|
+
|
|
+SELECT lowrite(0, 'abcdefghijklmnopqrstuvwxyz');
|
|
+ lowrite
|
|
+---------
|
|
+ 26
|
|
+(1 row)
|
|
+
|
|
+SELECT lo_close(0);
|
|
+ lo_close
|
|
+----------
|
|
+ 0
|
|
+(1 row)
|
|
+
|
|
+COMMIT;
|
|
+COMMIT
|
|
+-- getattr/setattr
|
|
+BEGIN;
|
|
+BEGIN
|
|
+SELECT lo_open(loid, x'20000'::int) FROM lolabel WHERE label = 'local';
|
|
+ lo_open
|
|
+---------
|
|
+ 0
|
|
+(1 row)
|
|
+
|
|
+SELECT lo_lseek(0, 0, 2); -- seek to end
|
|
+ lo_lseek
|
|
+----------
|
|
+ 26
|
|
+(1 row)
|
|
+
|
|
+SELECT lowrite(0, 'ABCDEFGHIJKLMNOPQRSTUVWXYZ');
|
|
+ lowrite
|
|
+---------
|
|
+ 26
|
|
+(1 row)
|
|
+
|
|
+SELECT lo_tell(0);
|
|
+ lo_tell
|
|
+---------
|
|
+ 52
|
|
+(1 row)
|
|
+
|
|
+SELECT lo_lseek(0, 0, 0); -- seek to head
|
|
+ lo_lseek
|
|
+----------
|
|
+ 0
|
|
+(1 row)
|
|
+
|
|
+SELECT loread(0, 50);
|
|
+ loread
|
|
+----------------------------------------------------
|
|
+ abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWX
|
|
+(1 row)
|
|
+
|
|
+SELECT lo_close(0);
|
|
+ lo_close
|
|
+----------
|
|
+ 0
|
|
+(1 row)
|
|
+
|
|
+COMMIT;
|
|
+COMMIT
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+SELECT sepgsql_getcon();
|
|
+ sepgsql_getcon
|
|
+-----------------------------------------------------
|
|
+ unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+(1 row)
|
|
+
|
|
+-- change security label
|
|
+BEGIN;
|
|
+BEGIN
|
|
+SELECT lo_open(loid, x'40000'::int) FROM lolabel; -- a seed of trouble
|
|
+ lo_open
|
|
+---------
|
|
+ 0
|
|
+ 1
|
|
+ 2
|
|
+ 3
|
|
+(4 rows)
|
|
+
|
|
+SELECT lo_set_security(loid, 'system_u:object_r:sepgsql_blob_t:s0:c4')
|
|
+ FROM lolabel WHERE label in ('normal', 'readonly');
|
|
+ lo_set_security
|
|
+-----------------
|
|
+ t
|
|
+ t
|
|
+(2 rows)
|
|
+
|
|
+SELECT lo_get_security(loid) FROM lolabel;
|
|
+ lo_get_security
|
|
+---------------------------------------------------------
|
|
+ system_u:object_r:sepgsql_blob_t:s0:c4
|
|
+ system_u:object_r:sepgsql_blob_t:s0:c4
|
|
+ system_u:object_r:sepgsql_secret_blob_t:s0
|
|
+ unconfined_u:object_r:sepgsql_test_sepgsql_blob_t:s0:c0
|
|
+(4 rows)
|
|
+
|
|
+SELECT security_context, lo_label(loid) AS label, count(*)
|
|
+ FROM pg_largeobject WHERE loid in (SELECT loid FROM lolabel)
|
|
+ GROUP BY security_context, loid ORDER BY label;
|
|
+ security_context | label | count
|
|
+---------------------------------------------------------+----------+-------
|
|
+ unconfined_u:object_r:sepgsql_test_sepgsql_blob_t:s0:c0 | local | 1
|
|
+ system_u:object_r:sepgsql_blob_t:s0:c4 | normal | 10
|
|
+ system_u:object_r:sepgsql_blob_t:s0:c4 | readonly | 10
|
|
+ system_u:object_r:sepgsql_secret_blob_t:s0 | secret | 10
|
|
+(4 rows)
|
|
+
|
|
+ROLLBACK;
|
|
+ROLLBACK
|
|
+-- cleanup
|
|
+SELECT lo_unlink(loid) FROM lolabel;
|
|
+ lo_unlink
|
|
+-----------
|
|
+ 1
|
|
+ 1
|
|
+ 1
|
|
+ 1
|
|
+(4 rows)
|
|
+
|
|
diff -rpNU3 base/src/test/sepgsql/expected/row_level.out sepgsql-new/src/test/sepgsql/expected/row_level.out
|
|
--- base/src/test/sepgsql/expected/row_level.out 1970-01-01 09:00:00.000000000 +0900
|
|
+++ sepgsql-new/src/test/sepgsql/expected/row_level.out 2009-03-02 00:24:34.000000000 +0900
|
|
@@ -0,0 +1,131 @@
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+SELECT sepgsql_getcon();
|
|
+ sepgsql_getcon
|
|
+-----------------------------------------------------
|
|
+ unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+(1 row)
|
|
+
|
|
+-- cleanup previous tests
|
|
+SET client_min_messages TO 'error';
|
|
+SET
|
|
+DROP TABLE IF EXISTS t4 CASCADE;
|
|
+DROP TABLE
|
|
+DROP TABLE IF EXISTS t3 CASCADE;
|
|
+DROP TABLE
|
|
+DROP TABLE IF EXISTS t2 CASCADE;
|
|
+DROP TABLE
|
|
+DROP TABLE IF EXISTS t1 CASCADE;
|
|
+DROP TABLE
|
|
+DROP FUNCTION IF EXISTS f1(int) CASCADE;
|
|
+DROP FUNCTION
|
|
+DROP FUNCTION IF EXISTS f2(int) CASCADE;
|
|
+DROP FUNCTION
|
|
+RESET client_min_messages;
|
|
+RESET
|
|
+-- test begins here
|
|
+CREATE TABLE t1 (
|
|
+ a int primary key,
|
|
+ b text
|
|
+);
|
|
+NOTICE: CREATE TABLE / PRIMARY KEY will create implicit index "t1_pkey" for table "t1"
|
|
+CREATE TABLE
|
|
+CREATE TABLE t2 (
|
|
+ x int references t1 (a) on update cascade,
|
|
+ y text
|
|
+);
|
|
+CREATE TABLE
|
|
+INSERT INTO t1 (security_context, a, b) VALUES
|
|
+ ('system_u:object_r:sepgsql_table_t:s0', 1, 'aaa'),
|
|
+ ('system_u:object_r:sepgsql_table_t:s0:c0', 2, 'bbb'),
|
|
+ ('system_u:object_r:sepgsql_table_t:s0:c1', 3, 'ccc'),
|
|
+ ('system_u:object_r:sepgsql_ro_table_t:s0', 4, 'ddd'),
|
|
+ ('system_u:object_r:sepgsql_ro_table_t:s0:c0', 5, 'eee'),
|
|
+ ('system_u:object_r:sepgsql_ro_table_t:s0:c1', 6, 'fff');
|
|
+INSERT 0 6
|
|
+INSERT INTO t2 (security_context, x, y) VALUES
|
|
+ ('system_u:object_r:sepgsql_table_t:s0:c1', 1, 'xxx'),
|
|
+ ('system_u:object_r:sepgsql_table_t:s0:c0', 2, 'yyy'),
|
|
+ ('system_u:object_r:sepgsql_table_t:s0', 3, 'zzz');
|
|
+INSERT 0 3
|
|
+SELECT security_context, * FROM t1;
|
|
+ security_context | a | b
|
|
+--------------------------------------------+---+-----
|
|
+ system_u:object_r:sepgsql_table_t:s0 | 1 | aaa
|
|
+ system_u:object_r:sepgsql_table_t:s0:c0 | 2 | bbb
|
|
+ system_u:object_r:sepgsql_table_t:s0:c1 | 3 | ccc
|
|
+ system_u:object_r:sepgsql_ro_table_t:s0 | 4 | ddd
|
|
+ system_u:object_r:sepgsql_ro_table_t:s0:c0 | 5 | eee
|
|
+ system_u:object_r:sepgsql_ro_table_t:s0:c1 | 6 | fff
|
|
+(6 rows)
|
|
+
|
|
+SELECT security_context, * FROM t2;
|
|
+ security_context | x | y
|
|
+-----------------------------------------+---+-----
|
|
+ system_u:object_r:sepgsql_table_t:s0:c1 | 1 | xxx
|
|
+ system_u:object_r:sepgsql_table_t:s0:c0 | 2 | yyy
|
|
+ system_u:object_r:sepgsql_table_t:s0 | 3 | zzz
|
|
+(3 rows)
|
|
+
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:sepgsql_test_t:s0:c0
|
|
+SELECT sepgsql_getcon();
|
|
+ sepgsql_getcon
|
|
+------------------------------------------------
|
|
+ unconfined_u:unconfined_r:sepgsql_test_t:s0:c0
|
|
+(1 row)
|
|
+
|
|
+SELECT security_context, * FROM t1;
|
|
+ security_context | a | b
|
|
+--------------------------------------------+---+-----
|
|
+ system_u:object_r:sepgsql_table_t:s0 | 1 | aaa
|
|
+ system_u:object_r:sepgsql_table_t:s0:c0 | 2 | bbb
|
|
+ system_u:object_r:sepgsql_ro_table_t:s0 | 4 | ddd
|
|
+ system_u:object_r:sepgsql_ro_table_t:s0:c0 | 5 | eee
|
|
+(4 rows)
|
|
+
|
|
+SELECT security_context, * FROM t2;
|
|
+ security_context | x | y
|
|
+-----------------------------------------+---+-----
|
|
+ system_u:object_r:sepgsql_table_t:s0:c0 | 2 | yyy
|
|
+ system_u:object_r:sepgsql_table_t:s0 | 3 | zzz
|
|
+(2 rows)
|
|
+
|
|
+COPY t1 TO stdout;
|
|
+1 aaa
|
|
+2 bbb
|
|
+4 ddd
|
|
+5 eee
|
|
+COPY t2 (security_context, x, y) TO stdout;
|
|
+system_u:object_r:sepgsql_table_t:s0:c0 2 yyy
|
|
+system_u:object_r:sepgsql_table_t:s0 3 zzz
|
|
+UPDATE t1 SET a = 99 WHERE a = 1 RETURNING *; -- to be failed
|
|
+ERROR: SELinux: security policy violation
|
|
+CONTEXT: SQL statement "UPDATE ONLY "public"."t2" SET "x" = $1 WHERE $2 OPERATOR(pg_catalog.=) "x""
|
|
+UPDATE t1 SET a = 99 WHERE a = 2 RETURNING *;
|
|
+ a | b
|
|
+----+-----
|
|
+ 99 | bbb
|
|
+(1 row)
|
|
+
|
|
+UPDATE 1
|
|
+UPDATE t1 SET a = 99 WHERE a = 4 RETURNING *; -- to be denied
|
|
+ a | b
|
|
+---+---
|
|
+(0 rows)
|
|
+
|
|
+UPDATE 0
|
|
+INSERT INTO t1 VALUES (3, 'ccc'); -- to be failed
|
|
+ERROR: duplicate key value violates unique constraint "t1_pkey"
|
|
+INSERT INTO t1 VALUES (7, 'ggg');
|
|
+INSERT 0 1
|
|
+INSERT INTO t2 VALUES (3, 'XXX'); -- to be failed
|
|
+ERROR: insert or update on table "t2" violates foreign key constraint "t2_x_fkey"
|
|
+DETAIL: Key (x)=(3) is not present in table "t1".
|
|
+INSERT INTO t2 VALUES (4, 'XXX');
|
|
+INSERT 0 1
|
|
+DELETE FROM t1; -- to be failed
|
|
+ERROR: SELinux: security policy violation
|
|
+CONTEXT: SQL statement "SELECT 1 FROM ONLY "public"."t2" x WHERE $1 OPERATOR(pg_catalog.=) "x" FOR SHARE OF x"
|
|
+DELETE FROM t1 WHERE a not in (SELECT x FROM t2); -- to be failed
|
|
+ERROR: SELinux: security policy violation
|
|
+DELETE FROM t1 WHERE a = 7;
|
|
+DELETE 1
|
|
diff -rpNU3 base/src/test/sepgsql/expected/security_label.out sepgsql-new/src/test/sepgsql/expected/security_label.out
|
|
--- base/src/test/sepgsql/expected/security_label.out 1970-01-01 09:00:00.000000000 +0900
|
|
+++ sepgsql-new/src/test/sepgsql/expected/security_label.out 2009-03-02 00:24:34.000000000 +0900
|
|
@@ -0,0 +1,127 @@
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+SELECT sepgsql_getcon();
|
|
+ sepgsql_getcon
|
|
+-----------------------------------------------------
|
|
+ unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+(1 row)
|
|
+
|
|
+-- cleanup previous tests
|
|
+SET client_min_messages TO 'error';
|
|
+SET
|
|
+DROP TABLE IF EXISTS t4 CASCADE;
|
|
+DROP TABLE
|
|
+DROP TABLE IF EXISTS t3 CASCADE;
|
|
+DROP TABLE
|
|
+DROP TABLE IF EXISTS t2 CASCADE;
|
|
+DROP TABLE
|
|
+DROP TABLE IF EXISTS t1 CASCADE;
|
|
+DROP TABLE
|
|
+DROP FUNCTION IF EXISTS f1(int) CASCADE;
|
|
+DROP FUNCTION
|
|
+DROP FUNCTION IF EXISTS f2(int) CASCADE;
|
|
+DROP FUNCTION
|
|
+RESET client_min_messages;
|
|
+RESET
|
|
+-- test begins here
|
|
+CREATE TABLE t1 (
|
|
+ a int,
|
|
+ b text
|
|
+);
|
|
+CREATE TABLE
|
|
+CREATE TABLE t2 (
|
|
+ x int,
|
|
+ y text
|
|
+);
|
|
+CREATE TABLE
|
|
+CREATE TABLE t3 (
|
|
+ s int,
|
|
+ t text
|
|
+) SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_fixed_table_t:s0';
|
|
+CREATE TABLE
|
|
+INSERT INTO t1 VALUES (1, 'aaa');
|
|
+INSERT 0 1
|
|
+INSERT INTO t1 (security_context, a, b) VALUES ('unconfined_u:object_r:sepgsql_ro_table_t:s0', 2, 'bbb');
|
|
+INSERT 0 1
|
|
+INSERT INTO t1 (security_context, a, b) VALUES ('unconfined_u:object_r:sepgsql_table_t:s0:c1', 3, 'ccc');
|
|
+INSERT 0 1
|
|
+INSERT INTO t1 VALUES (4, 'ddd'), (5, 'eee');
|
|
+INSERT 0 2
|
|
+INSERT INTO t1 (security_context, a, b) VALUES ('invalid security context', 6, 'fff'); -- to be failed
|
|
+ERROR: invalid security label: invalid security context
|
|
+INSERT INTO t1 (security_context, a, b) VALUES ('system_u:object_r:sepgsql_table_t:s0:c20', 6, 'fff'); -- to be denied
|
|
+INSERT 0 0
|
|
+SELECT security_context, * FROM t1;
|
|
+ security_context | a | b
|
|
+---------------------------------------------+---+-----
|
|
+ unconfined_u:object_r:sepgsql_table_t:s0 | 1 | aaa
|
|
+ unconfined_u:object_r:sepgsql_ro_table_t:s0 | 2 | bbb
|
|
+ unconfined_u:object_r:sepgsql_table_t:s0:c1 | 3 | ccc
|
|
+ unconfined_u:object_r:sepgsql_table_t:s0 | 4 | ddd
|
|
+ unconfined_u:object_r:sepgsql_table_t:s0 | 5 | eee
|
|
+(5 rows)
|
|
+
|
|
+INSERT INTO t2 (security_context, x, y)
|
|
+ (SELECT sepgsql_set_user(security_context, 'system_u'), a + 5, b || '_cpy' FROM t1);
|
|
+INSERT 0 5
|
|
+SELECT security_context, * FROM t2;
|
|
+ security_context | x | y
|
|
+-----------------------------------------+----+---------
|
|
+ system_u:object_r:sepgsql_table_t:s0 | 6 | aaa_cpy
|
|
+ system_u:object_r:sepgsql_ro_table_t:s0 | 7 | bbb_cpy
|
|
+ system_u:object_r:sepgsql_table_t:s0:c1 | 8 | ccc_cpy
|
|
+ system_u:object_r:sepgsql_table_t:s0 | 9 | ddd_cpy
|
|
+ system_u:object_r:sepgsql_table_t:s0 | 10 | eee_cpy
|
|
+(5 rows)
|
|
+
|
|
+INSERT INTO t3 VALUES (98, 'xxx');
|
|
+INSERT 0 1
|
|
+INSERT INTO t3 (security_context, s, t) VALUES ('system_u:object_r:sepgsql_ro_table_t:s0', 99, 'yyy');
|
|
+INSERT 0 1
|
|
+INSERT INTO t3 (SELECT * FROM t1);
|
|
+INSERT 0 5
|
|
+INSERT INTO t3 (security_context, s, t) (SELECT security_context, x, y FROM t2);
|
|
+INSERT 0 5
|
|
+SELECT security_context, * FROM t3;
|
|
+ security_context | s | t
|
|
+------------------------------------------------+----+---------
|
|
+ unconfined_u:object_r:sepgsql_fixed_table_t:s0 | 98 | xxx
|
|
+ system_u:object_r:sepgsql_ro_table_t:s0 | 99 | yyy
|
|
+ unconfined_u:object_r:sepgsql_fixed_table_t:s0 | 1 | aaa
|
|
+ unconfined_u:object_r:sepgsql_fixed_table_t:s0 | 2 | bbb
|
|
+ unconfined_u:object_r:sepgsql_fixed_table_t:s0 | 3 | ccc
|
|
+ unconfined_u:object_r:sepgsql_fixed_table_t:s0 | 4 | ddd
|
|
+ unconfined_u:object_r:sepgsql_fixed_table_t:s0 | 5 | eee
|
|
+ system_u:object_r:sepgsql_table_t:s0 | 6 | aaa_cpy
|
|
+ system_u:object_r:sepgsql_ro_table_t:s0 | 7 | bbb_cpy
|
|
+ system_u:object_r:sepgsql_table_t:s0:c1 | 8 | ccc_cpy
|
|
+ system_u:object_r:sepgsql_table_t:s0 | 9 | ddd_cpy
|
|
+ system_u:object_r:sepgsql_table_t:s0 | 10 | eee_cpy
|
|
+(12 rows)
|
|
+
|
|
+SELECT sepgsql_set_range(security_context, 's0:c' || s) AS security_context, * INTO t4 FROM t3; -- partially denied
|
|
+SELECT
|
|
+SELECT security_context, * FROM t4;
|
|
+ security_context | s | t
|
|
+---------------------------------------------------+----+---------
|
|
+ unconfined_u:object_r:sepgsql_fixed_table_t:s0:c1 | 1 | aaa
|
|
+ unconfined_u:object_r:sepgsql_fixed_table_t:s0:c2 | 2 | bbb
|
|
+ unconfined_u:object_r:sepgsql_fixed_table_t:s0:c3 | 3 | ccc
|
|
+ unconfined_u:object_r:sepgsql_fixed_table_t:s0:c4 | 4 | ddd
|
|
+ unconfined_u:object_r:sepgsql_fixed_table_t:s0:c5 | 5 | eee
|
|
+ system_u:object_r:sepgsql_table_t:s0:c6 | 6 | aaa_cpy
|
|
+ system_u:object_r:sepgsql_ro_table_t:s0:c7 | 7 | bbb_cpy
|
|
+ system_u:object_r:sepgsql_table_t:s0:c8 | 8 | ccc_cpy
|
|
+ system_u:object_r:sepgsql_table_t:s0:c9 | 9 | ddd_cpy
|
|
+ system_u:object_r:sepgsql_table_t:s0:c10 | 10 | eee_cpy
|
|
+(10 rows)
|
|
+
|
|
+COPY t1 (security_context, a, b) FROM stdin; -- partially denied
|
|
+COPY t1 (security_context, a, b) TO stdout;
|
|
+unconfined_u:object_r:sepgsql_table_t:s0 1 aaa
|
|
+unconfined_u:object_r:sepgsql_ro_table_t:s0 2 bbb
|
|
+unconfined_u:object_r:sepgsql_table_t:s0:c1 3 ccc
|
|
+unconfined_u:object_r:sepgsql_table_t:s0 4 ddd
|
|
+unconfined_u:object_r:sepgsql_table_t:s0 5 eee
|
|
+system_u:object_r:sepgsql_table_t:s0:c2 10 kkk
|
|
+system_u:object_r:sepgsql_table_t:s0:c3 11 lll
|
|
+system_u:object_r:sepgsql_table_t:s0:c4 13 nnn
|
|
diff -rpNU3 base/src/test/sepgsql/launch_psql.c sepgsql-new/src/test/sepgsql/launch_psql.c
|
|
--- base/src/test/sepgsql/launch_psql.c 1970-01-01 09:00:00.000000000 +0900
|
|
+++ sepgsql-new/src/test/sepgsql/launch_psql.c 2009-03-02 00:24:34.000000000 +0900
|
|
@@ -0,0 +1,87 @@
|
|
+/*
|
|
+ * launch_psql.c
|
|
+ *
|
|
+ * It invokes psql with proper security context.
|
|
+ */
|
|
+#include <stdio.h>
|
|
+#include <stdlib.h>
|
|
+#include <string.h>
|
|
+#include <unistd.h>
|
|
+#include <errno.h>
|
|
+#include <selinux/selinux.h>
|
|
+
|
|
+#define SETEXECCON_CMD "--@SECURITY_CONTEXT="
|
|
+
|
|
+int main(int argc, char *const argv[])
|
|
+{
|
|
+ char buffer[2048], cmd[512];
|
|
+ FILE *filp = NULL;
|
|
+ int i, ofs;
|
|
+
|
|
+ if (argc < 2)
|
|
+ {
|
|
+ fprintf(stderr, "usage: %s <command> [<options> ...]\n", argv[0]);
|
|
+ return 1;
|
|
+ }
|
|
+
|
|
+ for (i=1, ofs=0; argv[i] != NULL; i++)
|
|
+ ofs += snprintf(cmd + ofs, sizeof(cmd) - ofs, " %s", argv[i]);
|
|
+
|
|
+ while (fgets(buffer, sizeof(buffer), stdin) != NULL)
|
|
+ {
|
|
+ if (strncasecmp(buffer, SETEXECCON_CMD,
|
|
+ sizeof(SETEXECCON_CMD) - 1) == 0)
|
|
+ {
|
|
+ security_context_t context = buffer + sizeof(SETEXECCON_CMD) - 1;
|
|
+ char *pos;
|
|
+
|
|
+ /* set exec security context */
|
|
+ pos = strchr(context, '#');
|
|
+ if (pos)
|
|
+ *pos = '\0';
|
|
+ pos = context + strlen(context) - 1;
|
|
+ while (isspace(*pos))
|
|
+ *pos-- = '\0';
|
|
+ if (setexeccon(context) < 0)
|
|
+ {
|
|
+ fprintf(stderr, "%s: setexeccon('%s') = %s\n",
|
|
+ argv[0], context, strerror(errno));
|
|
+ return 1;
|
|
+ }
|
|
+
|
|
+ if (filp != NULL)
|
|
+ {
|
|
+ pclose(filp);
|
|
+ filp = NULL;
|
|
+ }
|
|
+
|
|
+ /* Inject a pseudo sepgsql_getcon() to confirm new context */
|
|
+ ofs = strlen(buffer);
|
|
+ snprintf(buffer + ofs, sizeof(buffer) - ofs,
|
|
+ "\nSELECT sepgsql_getcon();\n");
|
|
+ }
|
|
+
|
|
+ if (filp == NULL)
|
|
+ {
|
|
+ filp = popen(cmd, "w");
|
|
+ if (!filp)
|
|
+ {
|
|
+ fprintf(stderr, "%s: popen('%s', 'w') = %s\n",
|
|
+ argv[0], cmd, strerror(errno));
|
|
+ return 1;
|
|
+ }
|
|
+ }
|
|
+
|
|
+ if (fwrite(buffer, 1, strlen(buffer), filp) < 0)
|
|
+ {
|
|
+ fprintf(stderr, "%s: fwrite(...) = %s\n",
|
|
+ argv[0], strerror(errno));
|
|
+ return 1;
|
|
+ }
|
|
+ }
|
|
+
|
|
+ if (filp)
|
|
+ pclose(filp);
|
|
+
|
|
+ return 0;
|
|
+}
|
|
diff -rpNU3 base/src/test/sepgsql/sql/basic.sql sepgsql-new/src/test/sepgsql/sql/basic.sql
|
|
--- base/src/test/sepgsql/sql/basic.sql 1970-01-01 09:00:00.000000000 +0900
|
|
+++ sepgsql-new/src/test/sepgsql/sql/basic.sql 2009-03-02 00:24:34.000000000 +0900
|
|
@@ -0,0 +1,59 @@
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+
|
|
+-- cleanup previous tests
|
|
+SET client_min_messages TO 'error';
|
|
+
|
|
+DROP TABLE IF EXISTS t4 CASCADE;
|
|
+DROP TABLE IF EXISTS t3 CASCADE;
|
|
+DROP TABLE IF EXISTS t2 CASCADE;
|
|
+DROP TABLE IF EXISTS t1 CASCADE;
|
|
+
|
|
+DROP FUNCTION IF EXISTS f1(int) CASCADE;
|
|
+
|
|
+RESET client_min_messages;
|
|
+
|
|
+-- SETUP
|
|
+
|
|
+CREATE TABLE t1
|
|
+(
|
|
+ a int,
|
|
+ b text
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_ro_table_t:s0',
|
|
+ c bool
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_secret_table_t:s0'
|
|
+);
|
|
+INSERT INTO t1 VALUES (1, 'aaa', false), (2, 'bbb', true);
|
|
+
|
|
+CREATE TABLE t2
|
|
+(
|
|
+ s int,
|
|
+ t int,
|
|
+ u int
|
|
+) SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_table_t:s0:c0';
|
|
+ALTER TABLE t2 DROP COLUMN t; -- disturbing factor
|
|
+
|
|
+CREATE TABLE t3
|
|
+(
|
|
+ x text
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_table_t:s0:c1'
|
|
+) inherits(t2);
|
|
+
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0
|
|
+
|
|
+SELECT * FROM t1; -- to be denied
|
|
+SELECT a, b FROM t1;
|
|
+SELECT COUNT(*) FROM t1 WHERE c; -- to be denied
|
|
+UPDATE t1 SET b = 'ccc'; -- to be denied
|
|
+UPDATE t1 SET a = a + 2;
|
|
+INSERT INTO t1 VALUES (5, 'eee', true); -- to be denied
|
|
+INSERT INTO t1 VALUES (5);
|
|
+
|
|
+SELECT * FROM t2;
|
|
+SELECT t2 FROM t2;
|
|
+SELECT t3 FROM t3; -- to be denied
|
|
+SELECT 1 FROM t3;
|
|
+
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c1
|
|
+SELECT * FROM t2; -- to be denied
|
|
+SELECT t2 FROM t2; -- to be denied
|
|
+SELECT t3 FROM t3;
|
|
diff -rpNU3 base/src/test/sepgsql/sql/copy_stmt.sql sepgsql-new/src/test/sepgsql/sql/copy_stmt.sql
|
|
--- base/src/test/sepgsql/sql/copy_stmt.sql 1970-01-01 09:00:00.000000000 +0900
|
|
+++ sepgsql-new/src/test/sepgsql/sql/copy_stmt.sql 2009-03-02 00:24:34.000000000 +0900
|
|
@@ -0,0 +1,58 @@
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+
|
|
+-- cleanup previous tests
|
|
+SET client_min_messages TO 'error';
|
|
+
|
|
+DROP TABLE IF EXISTS t3 CASCADE;
|
|
+DROP TABLE IF EXISTS t2 CASCADE;
|
|
+DROP TABLE IF EXISTS t1 CASCADE;
|
|
+
|
|
+DROP FUNCTION IF EXISTS f1(int) CASCADE;
|
|
+
|
|
+RESET client_min_messages;
|
|
+
|
|
+-- setup tables
|
|
+
|
|
+CREATE TABLE t1
|
|
+(
|
|
+ a int,
|
|
+ b text
|
|
+);
|
|
+
|
|
+INSERT INTO t1 VALUES (1, 'aaa'), (2, 'bbb');
|
|
+
|
|
+CREATE TABLE t2
|
|
+(
|
|
+ x int,
|
|
+ y text
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_secret_table_t:s0'
|
|
+);
|
|
+SELECT security_context from pg_attribute where attrelid = 't2'::regclass and attname = 'y';
|
|
+INSERT INTO t2 VALUES (1, 'xxx'), (2, 'yyy');
|
|
+
|
|
+CREATE TABLE t3 -- read only table
|
|
+(
|
|
+ s int,
|
|
+ t text
|
|
+) SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_ro_table_t:s0';
|
|
+INSERT INTO t2 VALUES (1, 'sss'), (2, 'ttt');
|
|
+
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0
|
|
+COPY t1 TO stdout;
|
|
+COPY t1 FROM stdin;
|
|
+3 ccc
|
|
+4 ddd
|
|
+\.
|
|
+
|
|
+COPY t1 TO '/tmp/sepgsql_test_copy_1';
|
|
+COPY t1 TO '/tmp/sepgsql_test_copy_2'; -- to be denied
|
|
+
|
|
+COPY t2 TO stdout; -- to be denied
|
|
+COPY t2 FROM stdin; -- to be denied
|
|
+COPY t2 (x) TO stdout;
|
|
+
|
|
+COPY t3 TO stdout;
|
|
+COPY t3 FROM '/tmp/sepgsql_test_copy_1'; -- to be denied
|
|
+
|
|
+COPY t1 FROM '/tmp/sepgsql_test_copy_1';
|
|
+COPY t1 TO stdout;
|
|
diff -rpNU3 base/src/test/sepgsql/sql/enhanced_ddl_stmt.sql sepgsql-new/src/test/sepgsql/sql/enhanced_ddl_stmt.sql
|
|
--- base/src/test/sepgsql/sql/enhanced_ddl_stmt.sql 1970-01-01 09:00:00.000000000 +0900
|
|
+++ sepgsql-new/src/test/sepgsql/sql/enhanced_ddl_stmt.sql 2009-03-02 00:24:34.000000000 +0900
|
|
@@ -0,0 +1,89 @@
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+
|
|
+-- cleanup previous tests
|
|
+SET client_min_messages TO 'error';
|
|
+
|
|
+DROP TABLE IF EXISTS t4 CASCADE;
|
|
+DROP TABLE IF EXISTS t3 CASCADE;
|
|
+DROP TABLE IF EXISTS t2 CASCADE;
|
|
+DROP TABLE IF EXISTS t1 CASCADE;
|
|
+
|
|
+DROP FUNCTION IF EXISTS f1(int) CASCADE;
|
|
+DROP FUNCTION IF EXISTS f2(int) CASCADE;
|
|
+
|
|
+RESET client_min_messages;
|
|
+
|
|
+-- CREATE TABLE with SECURITY_LABEL clause
|
|
+CREATE TABLE t1 (
|
|
+ a int,
|
|
+ b text
|
|
+);
|
|
+SELECT relname, security_context FROM pg_class WHERE oid = 't1'::regclass;
|
|
+SELECT attname, security_context FROM pg_attribute WHERE attrelid = 't1'::regclass and attnum > 0;
|
|
+
|
|
+CREATE TABLE t2 (
|
|
+ a int,
|
|
+ b text
|
|
+) SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_ro_table_t:s0';
|
|
+SELECT relname, security_context FROM pg_class WHERE oid = 't2'::regclass;
|
|
+SELECT attname, security_context FROM pg_attribute WHERE attrelid = 't2'::regclass and attnum > 0;
|
|
+
|
|
+CREATE TABLE t3 (
|
|
+ a int,
|
|
+ b text SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_fixed_table_t:s0',
|
|
+ c bool SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_secret_table_t:s0',
|
|
+ d int
|
|
+) SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_table_t:s0:c0';
|
|
+SELECT relname, security_context FROM pg_class WHERE oid = 't3'::regclass;
|
|
+SELECT attname, security_context FROM pg_attribute WHERE attrelid = 't3'::regclass and attnum > 0;
|
|
+
|
|
+CREATE TABLE t4 (
|
|
+ a int,
|
|
+ b text
|
|
+) SECURITY_CONTEXT = 'unconfined_u:object_r:invalid_label_t:s0'; -- to be failed
|
|
+
|
|
+CREATE TABLE t4 (
|
|
+ a int,
|
|
+ b text
|
|
+) SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_proc_t:s0'; -- to be denied
|
|
+
|
|
+-- ALTER TABLE with SECURITY_CONTEXT clause
|
|
+ALTER TABLE t2 SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_secret_table_t:s0';
|
|
+ALTER TABLE t2 ADD COLUMN c bool; -- it inherits table's one
|
|
+SELECT relname, security_context FROM pg_class WHERE oid = 't2'::regclass;
|
|
+SELECT attname, security_context FROM pg_attribute WHERE attrelid = 't2'::regclass and attnum > 0;
|
|
+
|
|
+ALTER TABLE t3 ALTER b SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_table_t:s0';
|
|
+SELECT relname, security_context FROM pg_class WHERE oid = 't3'::regclass;
|
|
+SELECT attname, security_context FROM pg_attribute WHERE attrelid = 't3'::regclass and attnum > 0;
|
|
+
|
|
+-- CREATE FUNCTION with SECURITY_CONTEXT clause
|
|
+CREATE FUNCTION f1 (int) RETURNS int
|
|
+ LANGUAGE 'sql'
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_proc_t:s0:c0'
|
|
+ AS 'SELECT $1 * 2';
|
|
+SELECT proname, security_context FROM pg_proc WHERE oid = 'f1'::regproc;
|
|
+
|
|
+CREATE FUNCTION f2 (int) RETURNS int
|
|
+ LANGUAGE 'sql'
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:invalid_label_t:s0'
|
|
+ AS 'SELECT $1 + $1'; -- to be failed
|
|
+
|
|
+CREATE FUNCTION f2 (int) RETURNS int
|
|
+ LANGUAGE 'sql'
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_proc_t:s0:c16'
|
|
+ AS 'SELECT $1 + $1'; -- to be denied
|
|
+
|
|
+CREATE FUNCTION f2 (int) RETURNS int
|
|
+ LANGUAGE 'sql'
|
|
+ AS 'SELECT $1 + $1';
|
|
+SELECT proname, security_context FROM pg_proc WHERE oid = 'f2'::regproc;
|
|
+
|
|
+-- ALTER FUNCTION with SECURITY_CONTEXT clause
|
|
+ALTER FUNCTION f1(int)
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_proc_t:s0:c1';
|
|
+SELECT proname, security_context FROM pg_proc WHERE oid = 'f1'::regproc;
|
|
+
|
|
+ALTER FUNCTION f2(int)
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_proc_t:s0:c16'; -- to be denied
|
|
+SELECT proname, security_context FROM pg_proc WHERE oid = 'f2'::regproc;
|
|
diff -rpNU3 base/src/test/sepgsql/sql/join_query.sql sepgsql-new/src/test/sepgsql/sql/join_query.sql
|
|
--- base/src/test/sepgsql/sql/join_query.sql 1970-01-01 09:00:00.000000000 +0900
|
|
+++ sepgsql-new/src/test/sepgsql/sql/join_query.sql 2009-03-02 00:24:34.000000000 +0900
|
|
@@ -0,0 +1,50 @@
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+
|
|
+-- cleanup previous tests
|
|
+SET client_min_messages TO 'error';
|
|
+
|
|
+DROP TABLE IF EXISTS t4 CASCADE;
|
|
+DROP TABLE IF EXISTS t3 CASCADE;
|
|
+DROP TABLE IF EXISTS t2 CASCADE;
|
|
+DROP TABLE IF EXISTS t1 CASCADE;
|
|
+
|
|
+DROP FUNCTION IF EXISTS f1(int) CASCADE;
|
|
+
|
|
+RESET client_min_messages;
|
|
+
|
|
+-- SETUP
|
|
+CREATE TABLE t1
|
|
+(
|
|
+ a int,
|
|
+ b text,
|
|
+ c int
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_secret_table_t:s0'
|
|
+);
|
|
+INSERT INTO t1 VALUES (1, 'aaa'), (2, 'bbb'), (3, 'ccc');
|
|
+
|
|
+CREATE TABLE t2
|
|
+(
|
|
+ x int,
|
|
+ y text
|
|
+);
|
|
+INSERT INTO t2 VALUES (2, 'xxx'), (3, 'yyy'), (4,'zzz');
|
|
+
|
|
+CREATE TABLE t3
|
|
+(
|
|
+ d int
|
|
+) INHERITS (t1);
|
|
+INSERT INTO t3 VALUES (4, 'ddd'), (5, 'eee');
|
|
+
|
|
+CREATE TABLE t4
|
|
+(
|
|
+ z int
|
|
+ SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_secret_table_t:s0'
|
|
+) INHERITS (t2);
|
|
+INSERT INTO t2 VALUES (1, 'sss'), (5, 'ttt');
|
|
+
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:sepgsql_test_t:s0-s0:c0
|
|
+SELECT * FROM t1 JOIN t2 ON a = x; -- to be denied
|
|
+SELECT a, b, y FROM t1 JOIN t2 ON a = x;
|
|
+SELECT a, b, y FROM t1 JOIN t2 ON c = x; -- to be denied
|
|
+SELECT COUNT(*) FROM t1 JOIN t2 ON a = x;
|
|
+SELECT j FROM (t1 JOIN t2 ON a = x) AS j; -- to be denied
|
|
diff -rpNU3 base/src/test/sepgsql/sql/large_object.sql sepgsql-new/src/test/sepgsql/sql/large_object.sql
|
|
--- base/src/test/sepgsql/sql/large_object.sql 1970-01-01 09:00:00.000000000 +0900
|
|
+++ sepgsql-new/src/test/sepgsql/sql/large_object.sql 2009-03-03 14:31:40.000000000 +0900
|
|
@@ -0,0 +1,103 @@
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+
|
|
+-- cleanup previous tests
|
|
+SET client_min_messages TO 'error';
|
|
+
|
|
+DROP TABLE IF EXISTS lolabel CASCADE;
|
|
+DROP FUNCTION IF EXISTS lo_label(oid) CASCADE;
|
|
+
|
|
+RESET client_min_messages;
|
|
+
|
|
+CREATE TABLE lolabel(
|
|
+ loid oid,
|
|
+ label text
|
|
+);
|
|
+
|
|
+CREATE OR REPLACE FUNCTION lo_label(oid)
|
|
+ RETURNS TEXT LANGUAGE 'sql'
|
|
+ AS 'SELECT label FROM lolabel WHERE loid = $1';
|
|
+
|
|
+INSERT INTO lolabel (SELECT lo_import('/tmp/sepgsql_test_blob1'), 'normal');
|
|
+INSERT INTO lolabel (SELECT lo_import('/tmp/sepgsql_test_blob1'), 'readonly');
|
|
+INSERT INTO lolabel (SELECT lo_import('/tmp/sepgsql_test_blob1'), 'secret');
|
|
+
|
|
+SELECT lo_set_security(loid, 'system_u:object_r:sepgsql_blob_t:s0')
|
|
+ FROM lolabel WHERE label = 'normal';
|
|
+SELECT lo_set_security(loid, 'system_u:object_r:sepgsql_ro_blob_t:s0')
|
|
+ FROM lolabel WHERE label = 'readonly';
|
|
+SELECT lo_set_security(loid, 'system_u:object_r:sepgsql_secret_blob_t:s0')
|
|
+ FROM lolabel WHERE label = 'secret';
|
|
+
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:sepgsql_test_t:s0:c0
|
|
+
|
|
+SELECT lo_get_security(loid) FROM lolabel;
|
|
+
|
|
+SELECT security_context, lo_label(loid) AS label, COUNT(*)
|
|
+ FROM pg_largeobject GROUP BY security_context, loid ORDER by label;
|
|
+
|
|
+-- read large object
|
|
+BEGIN;
|
|
+SELECT lo_open(loid, x'40000'::int) FROM lolabel WHERE label = 'normal';
|
|
+SELECT loread(0, 32);
|
|
+ROLLBACK;
|
|
+
|
|
+BEGIN;
|
|
+SELECT lo_open(loid, x'40000'::int) FROM lolabel WHERE label = 'readonly';
|
|
+SELECT loread(0, 32);
|
|
+ROLLBACK;
|
|
+
|
|
+BEGIN;
|
|
+SELECT lo_open(loid, x'40000'::int) FROM lolabel WHERE label = 'secret';
|
|
+SELECT loread(0, 32); -- to be denied
|
|
+ROLLBACK;
|
|
+
|
|
+-- write large object
|
|
+BEGIN;
|
|
+SELECT lo_open(loid, x'20000'::int) FROM lolabel WHERE label = 'normal';
|
|
+SELECT lowrite(0, 'ABCDEFGHIJKLMNOPQRSTUVWXYZ');
|
|
+ROLLBACK;
|
|
+
|
|
+BEGIN;
|
|
+SELECT lo_open(loid, x'20000'::int) FROM lolabel WHERE label = 'readonly';
|
|
+SELECT lowrite(0, 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'); -- to be denied
|
|
+ROLLBACK;
|
|
+
|
|
+BEGIN;
|
|
+SELECT lo_open(loid, x'20000'::int) FROM lolabel WHERE label = 'secret';
|
|
+SELECT lowrite(0, 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'); -- to be denied
|
|
+ROLLBACK;
|
|
+
|
|
+-- create large object
|
|
+BEGIN;
|
|
+INSERT INTO lolabel (SELECT lo_create(6004), 'local');
|
|
+SELECT lo_open(loid, x'20000'::int) FROM lolabel WHERE label = 'local';
|
|
+SELECT lowrite(0, 'abcdefghijklmnopqrstuvwxyz');
|
|
+SELECT lo_close(0);
|
|
+COMMIT;
|
|
+
|
|
+-- getattr/setattr
|
|
+BEGIN;
|
|
+SELECT lo_open(loid, x'20000'::int) FROM lolabel WHERE label = 'local';
|
|
+SELECT lo_lseek(0, 0, 2); -- seek to end
|
|
+SELECT lowrite(0, 'ABCDEFGHIJKLMNOPQRSTUVWXYZ');
|
|
+SELECT lo_tell(0);
|
|
+SELECT lo_lseek(0, 0, 0); -- seek to head
|
|
+SELECT loread(0, 50);
|
|
+SELECT lo_close(0);
|
|
+COMMIT;
|
|
+
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+
|
|
+-- change security label
|
|
+BEGIN;
|
|
+SELECT lo_open(loid, x'40000'::int) FROM lolabel; -- a seed of trouble
|
|
+SELECT lo_set_security(loid, 'system_u:object_r:sepgsql_blob_t:s0:c4')
|
|
+ FROM lolabel WHERE label in ('normal', 'readonly');
|
|
+SELECT lo_get_security(loid) FROM lolabel;
|
|
+SELECT security_context, lo_label(loid) AS label, count(*)
|
|
+ FROM pg_largeobject WHERE loid in (SELECT loid FROM lolabel)
|
|
+ GROUP BY security_context, loid ORDER BY label;
|
|
+ROLLBACK;
|
|
+
|
|
+-- cleanup
|
|
+SELECT lo_unlink(loid) FROM lolabel;
|
|
diff -rpNU3 base/src/test/sepgsql/sql/row_level.sql sepgsql-new/src/test/sepgsql/sql/row_level.sql
|
|
--- base/src/test/sepgsql/sql/row_level.sql 1970-01-01 09:00:00.000000000 +0900
|
|
+++ sepgsql-new/src/test/sepgsql/sql/row_level.sql 2009-03-02 00:24:34.000000000 +0900
|
|
@@ -0,0 +1,61 @@
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+
|
|
+-- cleanup previous tests
|
|
+SET client_min_messages TO 'error';
|
|
+
|
|
+DROP TABLE IF EXISTS t4 CASCADE;
|
|
+DROP TABLE IF EXISTS t3 CASCADE;
|
|
+DROP TABLE IF EXISTS t2 CASCADE;
|
|
+DROP TABLE IF EXISTS t1 CASCADE;
|
|
+
|
|
+DROP FUNCTION IF EXISTS f1(int) CASCADE;
|
|
+DROP FUNCTION IF EXISTS f2(int) CASCADE;
|
|
+
|
|
+RESET client_min_messages;
|
|
+
|
|
+-- test begins here
|
|
+CREATE TABLE t1 (
|
|
+ a int primary key,
|
|
+ b text
|
|
+);
|
|
+
|
|
+CREATE TABLE t2 (
|
|
+ x int references t1 (a) on update cascade,
|
|
+ y text
|
|
+);
|
|
+
|
|
+INSERT INTO t1 (security_context, a, b) VALUES
|
|
+ ('system_u:object_r:sepgsql_table_t:s0', 1, 'aaa'),
|
|
+ ('system_u:object_r:sepgsql_table_t:s0:c0', 2, 'bbb'),
|
|
+ ('system_u:object_r:sepgsql_table_t:s0:c1', 3, 'ccc'),
|
|
+ ('system_u:object_r:sepgsql_ro_table_t:s0', 4, 'ddd'),
|
|
+ ('system_u:object_r:sepgsql_ro_table_t:s0:c0', 5, 'eee'),
|
|
+ ('system_u:object_r:sepgsql_ro_table_t:s0:c1', 6, 'fff');
|
|
+
|
|
+INSERT INTO t2 (security_context, x, y) VALUES
|
|
+ ('system_u:object_r:sepgsql_table_t:s0:c1', 1, 'xxx'),
|
|
+ ('system_u:object_r:sepgsql_table_t:s0:c0', 2, 'yyy'),
|
|
+ ('system_u:object_r:sepgsql_table_t:s0', 3, 'zzz');
|
|
+
|
|
+SELECT security_context, * FROM t1;
|
|
+SELECT security_context, * FROM t2;
|
|
+
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:sepgsql_test_t:s0:c0
|
|
+SELECT security_context, * FROM t1;
|
|
+SELECT security_context, * FROM t2;
|
|
+
|
|
+COPY t1 TO stdout;
|
|
+COPY t2 (security_context, x, y) TO stdout;
|
|
+
|
|
+UPDATE t1 SET a = 99 WHERE a = 1 RETURNING *; -- to be failed
|
|
+UPDATE t1 SET a = 99 WHERE a = 2 RETURNING *;
|
|
+UPDATE t1 SET a = 99 WHERE a = 4 RETURNING *; -- to be denied
|
|
+
|
|
+INSERT INTO t1 VALUES (3, 'ccc'); -- to be failed
|
|
+INSERT INTO t1 VALUES (7, 'ggg');
|
|
+INSERT INTO t2 VALUES (3, 'XXX'); -- to be failed
|
|
+INSERT INTO t2 VALUES (4, 'XXX');
|
|
+
|
|
+DELETE FROM t1; -- to be failed
|
|
+DELETE FROM t1 WHERE a not in (SELECT x FROM t2); -- to be failed
|
|
+DELETE FROM t1 WHERE a = 7;
|
|
diff -rpNU3 base/src/test/sepgsql/sql/security_label.sql sepgsql-new/src/test/sepgsql/sql/security_label.sql
|
|
--- base/src/test/sepgsql/sql/security_label.sql 1970-01-01 09:00:00.000000000 +0900
|
|
+++ sepgsql-new/src/test/sepgsql/sql/security_label.sql 2009-03-02 00:24:34.000000000 +0900
|
|
@@ -0,0 +1,60 @@
|
|
+--@SECURITY_CONTEXT=unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c15
|
|
+
|
|
+-- cleanup previous tests
|
|
+SET client_min_messages TO 'error';
|
|
+
|
|
+DROP TABLE IF EXISTS t4 CASCADE;
|
|
+DROP TABLE IF EXISTS t3 CASCADE;
|
|
+DROP TABLE IF EXISTS t2 CASCADE;
|
|
+DROP TABLE IF EXISTS t1 CASCADE;
|
|
+
|
|
+DROP FUNCTION IF EXISTS f1(int) CASCADE;
|
|
+DROP FUNCTION IF EXISTS f2(int) CASCADE;
|
|
+
|
|
+RESET client_min_messages;
|
|
+
|
|
+-- test begins here
|
|
+CREATE TABLE t1 (
|
|
+ a int,
|
|
+ b text
|
|
+);
|
|
+
|
|
+CREATE TABLE t2 (
|
|
+ x int,
|
|
+ y text
|
|
+);
|
|
+
|
|
+CREATE TABLE t3 (
|
|
+ s int,
|
|
+ t text
|
|
+) SECURITY_CONTEXT = 'unconfined_u:object_r:sepgsql_fixed_table_t:s0';
|
|
+
|
|
+INSERT INTO t1 VALUES (1, 'aaa');
|
|
+INSERT INTO t1 (security_context, a, b) VALUES ('unconfined_u:object_r:sepgsql_ro_table_t:s0', 2, 'bbb');
|
|
+INSERT INTO t1 (security_context, a, b) VALUES ('unconfined_u:object_r:sepgsql_table_t:s0:c1', 3, 'ccc');
|
|
+INSERT INTO t1 VALUES (4, 'ddd'), (5, 'eee');
|
|
+INSERT INTO t1 (security_context, a, b) VALUES ('invalid security context', 6, 'fff'); -- to be failed
|
|
+INSERT INTO t1 (security_context, a, b) VALUES ('system_u:object_r:sepgsql_table_t:s0:c20', 6, 'fff'); -- to be denied
|
|
+SELECT security_context, * FROM t1;
|
|
+
|
|
+INSERT INTO t2 (security_context, x, y)
|
|
+ (SELECT sepgsql_set_user(security_context, 'system_u'), a + 5, b || '_cpy' FROM t1);
|
|
+SELECT security_context, * FROM t2;
|
|
+
|
|
+INSERT INTO t3 VALUES (98, 'xxx');
|
|
+INSERT INTO t3 (security_context, s, t) VALUES ('system_u:object_r:sepgsql_ro_table_t:s0', 99, 'yyy');
|
|
+INSERT INTO t3 (SELECT * FROM t1);
|
|
+INSERT INTO t3 (security_context, s, t) (SELECT security_context, x, y FROM t2);
|
|
+SELECT security_context, * FROM t3;
|
|
+
|
|
+SELECT sepgsql_set_range(security_context, 's0:c' || s) AS security_context, * INTO t4 FROM t3; -- partially denied
|
|
+SELECT security_context, * FROM t4;
|
|
+
|
|
+COPY t1 (security_context, a, b) FROM stdin; -- partially denied
|
|
+system_u:object_r:sepgsql_table_t:s0:c2 10 kkk
|
|
+system_u:object_r:sepgsql_table_t:s0:c3 11 lll
|
|
+system_u:object_r:sepgsql_table_t:s0:c20 12 mmm
|
|
+system_u:object_r:sepgsql_table_t:s0:c4 13 nnn
|
|
+\.
|
|
+
|
|
+COPY t1 (security_context, a, b) TO stdout;
|