Google cam kết thúc đẩy công bằng chủng tộc cho Cộng đồng người da đen. Xem cách thực hiện.

Kiểm soát truy cập tùy ý (DAC)

Các đối tượng và dịch vụ hệ thống tập tin được thêm vào bản dựng thường cần các ID riêng biệt, duy nhất, được gọi là ID Android (AID). Hiện tại, nhiều tài nguyên như tệp và dịch vụ sử dụng AID cốt lõi (do Android xác định) một cách không cần thiết; trong nhiều trường hợp, bạn có thể sử dụng AID OEM (do OEM xác định) để thay thế.

Các phiên bản trước của Android (Android 7.x trở xuống) đã mở rộng cơ chế AID bằng cách sử dụng tệp android_filesystem_config.h dành riêng android_filesystem_config.h thiết bị để chỉ định khả năng của hệ thống tệp và / hoặc AID OEM tùy chỉnh. Tuy nhiên, hệ thống này không trực quan vì nó không hỗ trợ sử dụng tên đẹp cho AID OEM, yêu cầu bạn chỉ định số thô cho trường người dùng và nhóm mà không có cách nào để liên kết tên thân thiện với AID số.

Các phiên bản Android mới hơn (Android 8.0 trở lên) hỗ trợ một phương pháp mới để mở rộng khả năng của hệ thống tệp. Phương pháp mới này hỗ trợ những điều sau:

  • Nhiều vị trí nguồn cho tệp cấu hình (cho phép cấu hình bản dựng có thể mở rộng).
  • Kiểm tra sự tỉnh táo trong thời gian xây dựng của các giá trị AID OEM.
  • Tạo tiêu đề OEM AID tùy chỉnh có thể được sử dụng trong các tệp nguồn nếu cần.
  • Liên kết tên thân thiện với giá trị OEM AID thực tế. Hỗ trợ các đối số chuỗi không phải số cho người dùng và nhóm, tức là "foo" thay vì "2901".

Các cải tiến bổ sung bao gồm việc xóa mảng android_ids[] khỏi system/core/libcutils/include/private/android_filesystem_config.h . Mảng này hiện tồn tại trong Bionic dưới dạng một mảng được tạo hoàn toàn riêng tư, với các trình truy cập thông qua getpwnam()getgrnam() . (Điều này có tác dụng phụ là tạo ra các tệp nhị phân ổn định khi các AID cốt lõi được sửa đổi.) Để biết công cụ và tệp README có thêm chi tiết, hãy tham khảo build/make/tools/fs_config .

Thêm ID Android (AID)

Android 8.0 đã xóa mảng android_ids[] khỏi Dự án nguồn mở Android (AOSP). Thay vào đó, tất cả các tên thân thiện với AID được tạo từ tệp tiêu đề system/core/libcutils/include/private/android_filesystem_config.h khi tạo mảng Bionic android_ids[] . Mọi define khớp AID_* đều được công cụ chọn và * trở thành tên viết thường.

Ví dụ: trong private/android_filesystem_config.h :

#define AID_SYSTEM 1000

Trở thành:

  • Tên thân thiện: hệ thống
  • uid: 1000
  • gid: 1000

Để thêm AID lõi AOSP mới, chỉ cần thêm #define vào tệp tiêu đề android_filesystem_config.h . AID sẽ được tạo khi xây dựng và có sẵn cho các giao diện sử dụng đối số người dùng và nhóm. Công cụ xác nhận AID mới không nằm trong phạm vi APP hoặc OEM; nó cũng tôn trọng các thay đổi đối với các phạm vi đó và sẽ tự động định cấu hình lại khi có các thay đổi hoặc phạm vi OEM mới dành riêng.

Định cấu hình AID

Để bật cơ chế AID mới, hãy đặt TARGET_FS_CONFIG_GEN trong tệp BoardConfig.mk . Biến này chứa một danh sách các tệp cấu hình, cho phép bạn nối các tệp khi cần.

Theo quy ước, các tệp cấu hình sử dụng tên config.fs , nhưng trên thực tế, bạn có thể sử dụng bất kỳ tên nào. config.fs tệp config.fsđịnh dạng Python ConfigParser ini và bao gồm phần mũ (để định cấu hình khả năng của hệ thống tệp) và phần AID (để định cấu hình OEM AID).

Định cấu hình phần mũ

Phần mũ hỗ trợ thiết lập khả năng hệ thống tệp trên các đối tượng hệ thống tệp trong bản dựng (bản thân hệ thống tệp cũng phải hỗ trợ chức năng này).

Do việc chạy một dịch vụ ổn định dưới dạng root trong Android gây ra lỗi Bộ kiểm tra tương thích (CTS) , các yêu cầu trước đó để duy trì khả năng trong khi chạy quy trình hoặc dịch vụ liên quan đến việc thiết lập khả năng, sau đó sử dụng setuid / setgid thành AID thích hợp để chạy. Với mũ, bạn có thể bỏ qua các yêu cầu này và để nhân làm việc đó cho bạn. Khi quyền kiểm soát được giao cho main() , quy trình của bạn đã có các khả năng cần thiết để dịch vụ của bạn có thể sử dụng nhóm và người dùng không phải root (đây là cách ưu tiên để bắt đầu các dịch vụ đặc quyền).

Phần viết hoa sử dụng cú pháp sau:

Phần Giá trị Định nghĩa
[path] Đường dẫn hệ thống tệp để định cấu hình. Một đường dẫn kết thúc bằng / được coi là một dir, nếu không nó là một tệp.

Đó là một lỗi khi chỉ định nhiều phần có cùng [path] trong các tệp khác nhau. Trong các phiên bản Python <= 3.2, cùng một tệp có thể chứa các phần ghi đè phần trước đó; trong Python 3.2, nó được đặt ở chế độ nghiêm ngặt.
mode Chế độ tệp bát phân Chế độ tệp bát phân hợp lệ gồm ít nhất 3 chữ số. Nếu 3 được chỉ định, nó có tiền tố là 0, chế độ khác được sử dụng nguyên trạng.
user AID_ <người dùng> C define cho AID hợp lệ hoặc tên thân thiện (ví dụ: cả AID_RADIOradio đều được chấp nhận). Để xác định AID tùy chỉnh, hãy xem phần Định cấu hình AID .
group AID_ <nhóm> Giống như người dùng.
caps mũ lưỡi trai* Tên như được khai báo trong bionic/libc/kernel/uapi/linux/capability.h mà không có chữ CAP_ đứng đầu. Cho phép trường hợp hỗn hợp. Mũ cũng có thể là nguyên:
  • nhị phân (0b0101)
  • bát phân (0455)
  • int (42)
  • hex (0xFF)
Phân tách nhiều chữ hoa bằng cách sử dụng khoảng trắng.

Để biết ví dụ sử dụng, hãy xem Sử dụng khả năng của hệ thống tệp .

Định cấu hình phần AID

Phần AID chứa OEM AID và sử dụng cú pháp sau:

Phần Giá trị Định nghĩa
[AID_<name>] <name> có thể chứa các ký tự ở dạng chữ hoa, số và dấu gạch dưới đã đặt. Phiên bản chữ thường được sử dụng làm tên thân thiện. Tệp tiêu đề được tạo để bao gồm mã sử dụng AID_<name> chính xác.

Lỗi khi chỉ định nhiều phần có cùng AID_<name> (không phân biệt chữ hoa chữ thường với các ràng buộc giống như [path] ).

<name> phải bắt đầu bằng tên phân vùng để đảm bảo rằng nó không xung đột với các nguồn khác nhau.
value <số> Chuỗi số kiểu C hợp lệ (hex, bát phân, nhị phân và thập phân).

Đó là một lỗi khi chỉ định nhiều phần với cùng một giá trị tùy chọn.

Các tùy chọn giá trị phải được chỉ định trong phạm vi tương ứng với phân vùng được sử dụng trong <name> . Danh sách các phân vùng hợp lệ và phạm vi tương ứng của chúng được xác định trong system/core/libcutils/include/private/android_filesystem_config.h . Các tùy chọn là:
  • Phân vùng nhà cung cấp
    • AID_OEM_RESERVED_START (2900) - AID_OEM_RESERVED_END (2999)
    • AID_OEM_RESERVED_2_START (5000) - AID_OEM_RESERVED_2_END (5999)
  • Phân vùng hệ thống
    • AID_SYSTEM_RESERVED_START (6000) - AID_SYSTEM_RESERVED_END (6499)
  • Phân vùng ODM
    • AID_ODM_RESERVED_START (6500) - AID_ODM_RESERVED_END (6999)
  • Phân vùng sản phẩm
    • AID_PRODUCT_RESERVED_START (7000) - AID_PRODUCT_RESERVED_END (7499)
  • Phân vùng System_ext
    • AID_SYSTEM_EXT_RESERVED_START (7500) - AID_SYSTEM_EXT_RESERVED_END (7999)

Để biết các ví dụ sử dụng, hãy xem Xác định tên AID OEMSử dụng AID OEM .

Các ví dụ sử dụng

Các ví dụ sau trình bày chi tiết cách xác định và sử dụng OEM AID cũng như cách bật các khả năng của hệ thống tệp. Tên AID OEM ( [AID_ name ] ) phải bắt đầu bằng tên phân vùng, chẳng hạn như "nhà cung cấp_ " để đảm bảo chúng không xung đột với tên AOSP trong tương lai hoặc các phân vùng khác.

Xác định tên AID OEM

Để xác định AID OEM, hãy tạo tệp config.fs và đặt giá trị AID. Ví dụ: trong device/x/y/config.fs , hãy đặt như sau:

[AID_VENDOR_FOO]
value: 2900

Sau khi tạo tệp, hãy đặt biến TARGET_FS_CONFIG_GEN và trỏ đến biến đó trong BoardConfig.mk . Ví dụ: trong device/x/y/BoardConfig.mk , hãy đặt như sau:

TARGET_FS_CONFIG_GEN += device/x/y/config.fs

AID tùy chỉnh của bạn hiện có thể được hệ thống sử dụng rộng rãi trên một bản dựng mới.

Sử dụng AID OEM

Để sử dụng OEM AID, trong mã C của bạn, hãy bao gồm oemaids_headers trong Makefile được liên kết của bạn và thêm #include "generated_oem_aid.h" oemaids_headers #include "generated_oem_aid.h" , sau đó bắt đầu sử dụng các số nhận dạng đã khai báo. Ví dụ, trong my_file.c , hãy thêm thông tin sau:

#include "generated_oem_aid.h"
…

If (ipc->uid == AID_VENDOR_FOO) {
  // Do something
...

Trong tệp Android.bp liên kết của bạn, hãy thêm thông tin sau:

header_libs: ["oemaids_headers"],

Nếu bạn đang sử dụng tệp Android.mk , hãy thêm thông tin sau:

LOCAL_HEADER_LIBRARIES := oemaids_headers

Sử dụng tên thân thiện

Trong Android 9, bạn có thể sử dụng tên thân thiện cho bất kỳ giao diện nào hỗ trợ tên AID. Ví dụ:

  • Trong một lệnh chown trong some/init.rc :
    chown vendor_foo /vendor/some/vendor_foo/file
    
  • Trong một service trong some/init.rc :
    service vendor_foo /vendor/bin/foo_service
        user vendor_foo
        group vendor_foo
    

Bởi vì ánh xạ nội bộ từ tên thân thiện đến uid được thực hiện bởi /vendor/etc/passwd/vendor/etc/group , phân vùng nhà cung cấp phải được gắn kết.

Liên kết tên thân thiện

Android 9 bao gồm hỗ trợ liên kết tên thân thiện với giá trị OEM AID thực tế. Bạn có thể sử dụng đối số chuỗi không phải số cho người dùng và nhóm, tức là "nhà cung cấp_ foo" thay vì "2901".

Chuyển đổi từ AID sang tên thân thiện

Đối với OEM AID , Android 8.x yêu cầu sử dụng oem_#### với getpwnam và các chức năng tương tự, cũng như ở những nơi xử lý tra cứu qua getpwnam (chẳng hạn như tập lệnh init ). Trong Android 9, bạn có thể sử dụng getpwnamgetgrnam friends trong Bionic để chuyển đổi từ Android ID (AID) sang tên thân thiện và ngược lại.

Sử dụng các khả năng của hệ thống tệp

Để kích hoạt khả năng của hệ thống tệp, hãy tạo phần mũ trong tệp config.fs . Ví dụ: trong device/x/y/config.fs , hãy thêm phần sau:

[system/bin/foo_service]
mode: 0555
user: AID_VENDOR_FOO
group: AID_SYSTEM
caps: SYS_ADMIN | SYS_NICE

Sau khi tạo tệp, hãy đặt TARGET_FS_CONFIG_GEN trỏ đến tệp đó trong BoardConfig.mk . Ví dụ: trong device/x/y/BoardConfig.mk , hãy đặt như sau:

TARGET_FS_CONFIG_GEN += device/x/y/config.fs

Khi dịch vụ vendor_ foo được thực thi, nó bắt đầu với khả năng CAP_SYS_ADMINCAP_SYS_NICE mà không setuidsetgid cuộc gọi. Bên cạnh đó, vendor_ foo chính sách SELinux dịch vụ không còn cần khả năng setuidsetgid và có thể bị xóa.

Định cấu hình ghi đè (Android 6.x-7.x)

Android 6.0 đã định vị lại fs_config và các định nghĩa cấu trúc liên quan ( system/core/include/private/android_filesystem_config.h ) thành system/core/libcutils/fs_config.c nơi chúng có thể được cập nhật hoặc ghi đè bởi các tệp nhị phân được cài đặt trong /system/etc/fs_config_dirs/system/etc/fs_config_files . Việc sử dụng các quy tắc đối sánh và phân tích cú pháp riêng biệt cho các thư mục và tệp (có thể sử dụng các biểu thức toàn cầu bổ sung) đã cho phép Android xử lý các thư mục và tệp trong hai bảng khác nhau. Các định nghĩa cấu trúc trong system/core/libcutils/fs_config.c không chỉ cho phép đọc thư mục và tệp trong thời gian chạy mà máy chủ có thể sử dụng các tệp giống nhau trong thời gian xây dựng để tạo hình ảnh hệ thống tệp là ${OUT}/system/etc/fs_config_dirs${OUT}/system/etc/fs_config_files .

Mặc dù phương pháp ghi đè mở rộng hệ thống tệp đã được thay thế bằng hệ thống cấu hình mô-đun được giới thiệu trong Android 8.0, bạn vẫn có thể sử dụng phương pháp cũ nếu muốn. Các phần sau trình bày chi tiết cách tạo và bao gồm các tệp ghi đè và định cấu hình hệ thống tệp.

Tạo tệp ghi đè

Bạn có thể tạo tệp nhị phân được căn chỉnh /system/etc/fs_config_dirs/system/etc/fs_config_files bằng cách sử dụng công cụ fs_config_generate trong build/tools/fs_config . Công cụ này sử dụng một libcutils thư viện libcutils ( fs_config_generate() ) để quản lý các yêu cầu DAC vào bộ đệm và xác định các quy tắc cho một tệp bao gồm để thể chế hóa các quy tắc DAC.

Để sử dụng, hãy tạo một tệp bao gồm trong device/ vendor / device /android_filesystem_config.h đóng vai trò ghi đè. Tệp phải sử dụng structure fs_path_config định dạng structure fs_path_config được xác định trong system/core/include/private/android_filesystem_config.h với các khởi tạo cấu trúc sau cho các ký hiệu thư mục và tệp:

  • Đối với thư mục, hãy sử dụng android _device _dirs[] .
  • Đối với tệp, hãy sử dụng android _device _files[] .

Khi không sử dụng android_device_dirs[]android_device_files[] , bạn có thể xác định NO_ANDROID_FILESYSTEM_CONFIG_DEVICE_DIRSNO_ANDROID_FILESYSTEM_CONFIG_DEVICE_FILES (xem ví dụ bên dưới). Bạn cũng có thể chỉ định tệp ghi đè bằng TARGET_ANDROID_FILESYSTEM_CONFIG_H trong cấu hình bảng, với tên cơ sở được thực thi là android_filesystem_config.h .

Bao gồm các tệp ghi đè

Để bao gồm các tệp, hãy đảm bảo rằng PRODUCT_PACKAGES bao gồm fs_config_dirs và / hoặc fs_config_files để có thể cài đặt chúng vào /system/etc/fs_config_dirs/system/etc/fs_config_files , tương ứng. Hệ thống xây dựng tìm kiếm android_filesystem_config.h tùy chỉnh trong $(TARGET_DEVICE_DIR) , nơi BoardConfig.mk tồn tại. Nếu tệp này tồn tại ở nơi khác, hãy đặt biến cấu hình bảng TARGET_ANDROID_FILESYSTEM_CONFIG_H để trỏ đến vị trí đó.

Định cấu hình hệ thống tệp

Để định cấu hình hệ thống tệp trong Android 6.0 trở lên:

  1. Tạo tệp $(TARGET_DEVICE_DIR)/android_filesystem_config.h .
  2. Thêm fs_config_dirs và / hoặc fs_config_files vào PRODUCT_PACKAGES trong tệp cấu hình bảng (ví dụ: $(TARGET_DEVICE_DIR)/device.mk ).

Ghi đè ví dụ

Ví dụ này cho thấy một bản vá để ghi đè daemon system/bin/glgps để thêm hỗ trợ khóa đánh thức trong thư mục device/ vendor / device . Hãy ghi nhớ những điều sau:

  • Mỗi mục cấu trúc là chế độ, uid, gid, khả năng và tên. system/core/include/private/android_filesystem_config.h được tự động đưa vào để cung cấp AID_ROOT tệp kê khai ( AID_ROOT , AID_SHELL , CAP_BLOCK_SUSPEND ).
  • Phần android_device_files[] bao gồm một hành động ngăn chặn quyền truy cập vào system/etc/fs_config_dirs khi không được chỉ định, đóng vai trò như một biện pháp bảo vệ DAC bổ sung cho việc thiếu nội dung ghi đè thư mục. Tuy nhiên, đây là khả năng bảo vệ yếu; nếu ai đó có quyền kiểm soát /system , họ có thể làm bất cứ điều gì họ muốn.
diff --git a/android_filesystem_config.h b/android_filesystem_config.h
new file mode 100644
index 0000000..874195f
--- /dev/null
+++ b/android_filesystem_config.h
@@ -0,0 +1,36 @@
+/*
+ * Copyright (C) 2015 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ * implied. See the License for the specific language governing
+ * permissions and limitations under the License.
+ */
+
+/* This file is used to define the properties of the filesystem
+** images generated by build tools (eg: mkbootfs) and
+** by the device side of adb.
+*/
+
+#define NO_ANDROID_FILESYSTEM_CONFIG_DEVICE_DIRS
+/* static const struct fs_path_config android_device_dirs[] = { }; */
+
+/* Rules for files.
+** These rules are applied based on "first match", so they
+** should start with the most specific path and work their
+** way up to the root. Prefixes ending in * denotes wildcard
+** and will allow partial matches.
+*/
+static const struct fs_path_config android_device_files[] = {
+  { 00755, AID_ROOT, AID_SHELL, (1ULL << CAP_BLOCK_SUSPEND),
"system/bin/glgps" },
+#ifdef NO_ANDROID_FILESYSTEM_CONFIG_DEVICE_DIRS
+  { 00000, AID_ROOT, AID_ROOT, 0, "system/etc/fs_config_dirs" },
+#endif
+};


diff --git a/device.mk b/device.mk
index 0c71d21..235c1a7 100644
--- a/device.mk
+++ b/device.mk
@@ -18,7 +18,8 @@ PRODUCT_PACKAGES := \
     libwpa_client \
     hostapd \
     wpa_supplicant \
-    wpa_supplicant.conf
+    wpa_supplicant.conf \
+    fs_config_files

 ifeq ($(TARGET_PREBUILT_KERNEL),)
 ifeq ($(USE_SVELTE_KERNEL), true)

Di chuyển hệ thống tệp từ các bản phát hành trước đó

Khi di chuyển hệ thống tệp từ Android 5.x trở về trước, hãy nhớ rằng Android 6.x

  • Loại bỏ một số bao gồm, cấu trúc và định nghĩa nội tuyến.
  • Yêu cầu tham chiếu đến libcutils thay vì chạy trực tiếp từ system/core/include/private/android_filesystem_config.h . Các tệp thi hành riêng của nhà sản xuất thiết bị phụ thuộc vào system/code/include/private_filesystem_config.h cho cấu trúc tệp hoặc thư mục hoặc fs_config phải thêm phụ thuộc thư viện libcutils .
  • Yêu cầu nhà sản xuất thiết bị bản sao nhánh riêng của system/core/include/private/android_filesystem_config.h với nội dung bổ sung về các mục tiêu hiện có để chuyển đến device/ vendor / device /android_filesystem_config.h .
  • Bảo lưu quyền áp dụng Kiểm soát Truy cập Bắt buộc (MAC) của SELinux cho các tệp cấu hình trên hệ thống đích, các triển khai bao gồm các tệp thực thi mục tiêu tùy chỉnh sử dụng fs_config() phải đảm bảo quyền truy cập.