From 03ce5120722b3b5cb9cd0fec08c22681a96ee3d6 Mon Sep 17 00:00:00 2001
From: Nick Kralevich <nnk@google.com>
Date: Tue, 20 May 2014 11:09:16 -0700
Subject: [PATCH] Remove /system write from unconfined

Don't allow writes to /system from unconfined domains.
/system is always mounted read-only, and no process should
ever need to write there.

Allow recovery to write to /system. This is needed to apply OTA
images.

Change-Id: I11aa8bd0c3b7f53ebe83806a0547ab8d5f25f3c9
---
 domain.te     | 4 ++++
 init.te       | 3 ++-
 kernel.te     | 3 ++-
 recovery.te   | 6 +++++-
 unconfined.te | 8 ++++++--
 5 files changed, 19 insertions(+), 5 deletions(-)

diff --git a/domain.te b/domain.te
index eebe1a5c7..e27797267 100644
--- a/domain.te
+++ b/domain.te
@@ -250,3 +250,7 @@ neverallow {
 # Only the init property service should write to /data/property.
 neverallow { domain -init } property_data_file:dir { create setattr relabelfrom rename write add_name remove_name rmdir };
 neverallow { domain -init } property_data_file:file { create setattr relabelfrom write append unlink link rename };
+
+# Only recovery should be doing writes to /system
+neverallow { domain -recovery } { system_file exec_type }:dir_file_class_set
+    { create write setattr relabelfrom relabelto append unlink link rename };
diff --git a/init.te b/init.te
index f0c6ac6d9..f0e11f639 100644
--- a/init.te
+++ b/init.te
@@ -10,7 +10,8 @@ allow init self:capability { sys_rawio mknod };
 
 allow init dev_type:blk_file rw_file_perms;
 allow init fs_type:filesystem *;
-allow init {fs_type dev_type file_type}:dir_file_class_set relabelto;
+allow init {fs_type dev_type}:dir_file_class_set relabelto;
+allow init {file_type -system_file -exec_type}:dir_file_class_set relabelto;
 allow init kernel:security load_policy;
 allow init kernel:system syslog_mod;
 allow init usermodehelper:file rw_file_perms;
diff --git a/kernel.te b/kernel.te
index f2405e4fd..b09c10648 100644
--- a/kernel.te
+++ b/kernel.te
@@ -8,7 +8,8 @@ allow kernel init:process dyntransition;
 # The kernel is unconfined.
 unconfined_domain(kernel)
 
-allow kernel {fs_type dev_type file_type}:dir_file_class_set relabelto;
+allow kernel {fs_type dev_type}:dir_file_class_set relabelto;
+allow kernel {file_type -system_file -exec_type}:dir_file_class_set relabelto;
 allow kernel unlabeled:filesystem mount;
 allow kernel fs_type:filesystem *;
 
diff --git a/recovery.te b/recovery.te
index c1329833a..811623e62 100644
--- a/recovery.te
+++ b/recovery.te
@@ -5,10 +5,14 @@ unconfined_domain(recovery)
 
 allow recovery self:capability2 mac_admin;
 
-allow recovery {fs_type dev_type -kmem_device file_type}:dir_file_class_set relabelto;
+allow recovery {dev_type -kmem_device}:dir_file_class_set relabelto;
+allow recovery {fs_type file_type}:dir_file_class_set relabelto;
 allow recovery unlabeled:filesystem mount;
 allow recovery fs_type:filesystem *;
 
+allow recovery exec_type:{ file dir lnk_file } { create write setattr relabelfrom relabelto append unlink link rename };
+allow recovery system_file:{ file dir lnk_file } { create write setattr relabelfrom relabelto append unlink link rename };
+
 # Required to e.g. wipe userdata/cache.
 allow recovery dev_type:blk_file rw_file_perms;
 
diff --git a/unconfined.te b/unconfined.te
index 2302279b9..ecfe61574 100644
--- a/unconfined.te
+++ b/unconfined.te
@@ -28,10 +28,14 @@ allow unconfineddomain domain:{ fifo_file file } rw_file_perms;
 allow unconfineddomain domain:socket_class_set *;
 allow unconfineddomain domain:ipc_class_set *;
 allow unconfineddomain domain:key *;
-allow unconfineddomain {fs_type dev_type file_type -keystore_data_file -property_data_file}:{ dir lnk_file sock_file fifo_file } ~relabelto;
+allow unconfineddomain {fs_type dev_type}:{ dir lnk_file sock_file fifo_file } ~relabelto;
+allow unconfineddomain {file_type -keystore_data_file -property_data_file -system_file -exec_type}:{ dir lnk_file sock_file fifo_file } ~relabelto;
+allow unconfineddomain exec_type:{ file dir lnk_file } ~{ create write setattr relabelfrom relabelto append unlink link rename };
+allow unconfineddomain system_file:{ dir lnk_file } ~{ create write setattr relabelfrom relabelto append unlink link rename };
+allow unconfineddomain system_file:file ~{ create write setattr relabelfrom relabelto append unlink link rename entrypoint };
 allow unconfineddomain {fs_type -usermodehelper -proc_security}:{ chr_file file } ~{entrypoint execmod execute relabelto};
 allow unconfineddomain {dev_type -kmem_device}:{ chr_file file } ~{entrypoint execmod execute relabelto};
-allow unconfineddomain {file_type -keystore_data_file -property_data_file}:{ chr_file file } ~{entrypoint execmod execute relabelto};
+allow unconfineddomain {file_type -keystore_data_file -property_data_file -system_file -exec_type}:{ chr_file file } ~{entrypoint execmod execute relabelto};
 allow unconfineddomain { rootfs system_file exec_type }:file execute;
 allow unconfineddomain node_type:node *;
 allow unconfineddomain node_type:{ tcp_socket udp_socket rawip_socket } node_bind;
-- 
GitLab