Дискреционный контроль доступа (DAC)

Объектам и службам файловой системы, добавляемым в сборку, часто требуются отдельные уникальные идентификаторы, известные как идентификаторы Android (AID). В настоящее время многие ресурсы, такие как файлы и службы, без необходимости используют базовые (определенные Android) AID; во многих случаях вместо этого можно использовать OEM (определенные OEM) AID.

Earlier versions of Android (Android 7.x and lower) extended the AIDs mechanism using a device-specific android_filesystem_config.h file to specify file system capabilities and/or custom OEM AIDs. Однако эта система была неинтуитивной, поскольку она не поддерживала использование красивых имен для OEM-AID, требуя от вас указания необработанных числовых значений для полей пользователя и группы без возможности связать понятное имя с числовым AID.

Новые версии Android (Android 8.0 и выше) поддерживают новый метод расширения возможностей файловой системы. Этот новый метод поддерживает следующее:

  • Несколько исходных расположений для файлов конфигурации (обеспечивает расширяемые конфигурации сборки).
  • Проверка работоспособности значений OEM AID во время сборки.
  • Создание пользовательского заголовка OEM AID, который при необходимости можно использовать в исходных файлах.
  • Ассоциация понятного имени с фактическим значением OEM AID. Поддерживает нечисловые строковые аргументы для пользователя и группы, т. е. «foo» вместо «2901».

Дополнительные улучшения включают удаление массива android_ids[] из system/core/libcutils/include/private/android_filesystem_config.h . This array now exists in Bionic as a fully private generated array, with accessors with getpwnam() and getgrnam() . (This has the side effect of producing stable binaries as core AIDs are modified.) For tooling and a README file with more details, refer to build/make/tools/fs_config .

Добавить идентификаторы Android (AID)

Android 8.0 removed the android_ids[] array from the Android Open Source Project (AOSP). Вместо этого все имена, совместимые с AID, генерируются из заголовочного файла system/core/libcutils/include/private/android_filesystem_config.h при создании массива Bionic android_ids[] . Any define matching AID_* is picked up by the tooling and * becomes the lowercase name.

Например, в private/android_filesystem_config.h :

#define AID_SYSTEM 1000

Становится:

  • Понятное имя: система
  • идентификатор: 1000
  • гид: 1000

To add a new AOSP core AID, simply add the #define to the android_filesystem_config.h header file. AID генерируется при сборке и становится доступным для интерфейсов, использующих аргументы пользователя и группы. Инструменты подтверждают, что новый AID не соответствует диапазонам APP или OEM; он также учитывает изменения в этих диапазонах и должен автоматически перенастраиваться при изменениях или новых диапазонах, зарезервированных OEM.

Настройка идентификаторов AID

To enable the new AIDs mechanism, set TARGET_FS_CONFIG_GEN in the BoardConfig.mk file. Эта переменная содержит список файлов конфигурации, что позволяет добавлять файлы по мере необходимости.

By convention, configuration files use the name config.fs , but in practice you can use any name. config.fs files are in the Python ConfigParser ini format and include a caps section (for configuring file system capabilities) and an AIDs section (for configuring OEM AIDs).

Настройте раздел Caps

The caps section supports setting file system capabilities on file system objects within the build (the file system itself must also support this functionality).

Поскольку запуск стабильной службы с правами root в Android приводит к сбою пакета тестов совместимости (CTS) , предыдущие требования для сохранения возможности во время запуска процесса или службы включали настройку возможностей, а затем использование setuid / setgid для правильного запуска AID. Используя ограничения, вы можете пропустить эти требования и позволить ядру сделать это за вас. When control is handed to main() , your process already has the capabilities it needs so your service can use a nonroot user and group (this is the preferred way for starting privileged services).

В разделе caps используется следующий синтаксис:

Раздел Ценить Определение
[path] Путь файловой системы для настройки. Путь, заканчивающийся на /, считается каталогом, в противном случае это файл.

Указание нескольких разделов с одним и тем же [path] в разных файлах является ошибкой. В версиях Python <= 3.2 один и тот же файл может содержать разделы, переопределяющие предыдущий раздел; в Python 3.2 установлен строгий режим.
mode Восьмеричный файловый режим Допустимый восьмеричный формат файла, содержащий не менее 3 цифр. Если указано 3, перед ним ставится префикс 0, в противном случае режим используется как есть.
user AID_<пользователь> Either the C define for a valid AID or the friendly name (eg both AID_RADIO and radio are acceptable). Чтобы определить пользовательскую помощь, см. Настройку раздела помощи .
group AID_<группа> То же, что пользователь.
caps кепка* Имя, объявленное в bionic/libc/kernel/uapi/linux/capability.h без начального CAP_ . Допускается смешанный случай. Шапки также могут быть сырыми:
  • двоичный (0b0101)
  • восьмеричный (0455)
  • интервал (42)
  • шестнадцатеричный (0xFF)
Разделите несколько колпачков, используя пробелы.

Пример использования см. в разделе Использование возможностей файловой системы .

Настройте раздел помощи

Раздел AID содержит идентификаторы OEM AID и использует следующий синтаксис:

Раздел Ценить Определение
[AID_<name>] <name> может содержать символы в верхнем регистре, цифры и символы подчеркивания. Версия в нижнем регистре используется в качестве понятного имени. The generated header file for code inclusion uses the exact AID_<name> .

Указание нескольких разделов с одним и тем же AID_<name> (без учета регистра с теми же ограничениями, что и [path] ) является ошибкой.

<name> должно начинаться с имени раздела, чтобы оно не конфликтовало с разными источниками.
value <номер> Допустимая числовая строка в стиле C (шестнадцатеричная, восьмеричная, двоичная и десятичная).

Указание нескольких разделов с одинаковым значением параметра является ошибкой.

Опции значений должны быть указаны в диапазоне, соответствующем разделу, используемому в <name> . Список допустимых разделов и соответствующие им диапазоны определены в system/core/libcutils/include/private/android_filesystem_config.h . Возможные варианты:
  • Раздел поставщиков
    • AID_OEM_RESERVED_START(2900) – AID_OEM_RESERVED_END(2999)
    • AID_OEM_RESERVED_2_START(5000) – AID_OEM_RESERVED_2_END(5999)
  • Системный раздел
    • AID_SYSTEM_RESERVED_START(6000) - AID_SYSTEM_RESERVED_END(6499)
  • ОДМ-раздел
    • AID_ODM_RESERVED_START(6500) – AID_ODM_RESERVED_END(6999)
  • Раздел продукта
    • AID_PRODUCT_RESERVED_START(7000) – AID_PRODUCT_RESERVED_END(7499)
  • Раздел System_ext
    • AID_SYSTEM_EXT_RESERVED_START(7500) - AID_SYSTEM_EXT_RESERVED_END(7999)

For usage examples, see Defining OEM AID names and Using OEM AIDs .

Примеры использования

В следующих примерах подробно описано, как определить и использовать OEM AID и как включить возможности файловой системы. Имена OEM AID ( [AID_ name ] ) должны начинаться с имени раздела, например « vendor_ », чтобы гарантировать, что они не конфликтуют с будущими именами AOSP или другими разделами.

Определите имена OEM AID

Чтобы определить OEM AID, создайте файл config.fs и задайте значение AID. For example, in device/x/y/config.fs , set the following:

[AID_VENDOR_FOO]
value: 2900

После создания файла установите переменную TARGET_FS_CONFIG_GEN и укажите ее в BoardConfig.mk . For example, in device/x/y/BoardConfig.mk , set the following:

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

Ваш собственный AID теперь может использоваться системой в целом в новой сборке.

Используйте OEM-помощники

To use an OEM AID, in your C code, include the oemaids_headers in your associated Makefile, and add #include "generated_oem_aid.h" , then start using the declared identifiers. For example, in my_file.c , add the following:

#include "generated_oem_aid.h"


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

В связанный файл Android.bp добавьте следующее:

header_libs: ["oemaids_headers"],

Если вы используете файл Android.mk , добавьте следующее:

LOCAL_HEADER_LIBRARIES := oemaids_headers

Используйте понятные имена

В Android 9 вы можете использовать понятное имя для любого интерфейса, поддерживающего имена AID. Например:

  • In a chown command in some/init.rc :
    chown vendor_foo /vendor/some/vendor_foo/file
    
  • В service some/init.rc :
    service vendor_foo /vendor/bin/foo_service
        user vendor_foo
        group vendor_foo
    

Because the internal mapping from friendly name to uid is performed by /vendor/etc/passwd and /vendor/etc/group , the vendor partition must be mounted.

Ассоциированные понятные имена

Android 9 включает поддержку связывания понятного имени с фактическим значением OEM AID. You can use nonnumeric string arguments for user and group, that is, " vendor_ foo" instead of "2901".

Преобразование из AID в понятные имена

For OEM AIDs , Android 8.x required the use of oem_#### with getpwnam and similar functions, as well in places that handle lookups with getpwnam (such as init scripts). In Android 9, you can use the getpwnam and getgrnam friends in Bionic for converting from Android IDs (AIDs) to friendly names and vice versa.

Используйте возможности файловой системы

Чтобы включить возможности файловой системы, создайте раздел caps в файле config.fs . Например, в device/x/y/config.fs добавьте следующий раздел:

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

После создания файла установите TARGET_FS_CONFIG_GEN так, чтобы он указывал на этот файл в BoardConfig.mk . Например, в device/x/y/BoardConfig.mk установите следующее:

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

Когда выполняется vendor_ foo , она начинается с возможностей CAP_SYS_ADMIN и CAP_SYS_NICE без вызовов setuid и setgid . Кроме того, политика SELinux vendor_ foo больше не требует возможности setuid и setgid и может быть удалена.

Настройка переопределений (Android 6.x-7.x)

Android 6.0 relocated fs_config and associated structure definitions ( system/core/include/private/android_filesystem_config.h ) to system/core/libcutils/fs_config.c where they could be updated or overridden by binary files installed in /system/etc/fs_config_dirs and /system/etc/fs_config_files . Использование отдельных правил сопоставления и анализа для каталогов и файлов (которые могут использовать дополнительные выражения glob) позволило Android обрабатывать каталоги и файлы в двух разных таблицах. Structure definitions in system/core/libcutils/fs_config.c not only allowed runtime reading of directories and files, but the host could use the same files during build time to construct file system images as ${OUT}/system/etc/fs_config_dirs and ${OUT}/system/etc/fs_config_files .

Хотя метод переопределения расширения файловой системы был заменен модульной системой конфигурации, представленной в Android 8.0, при желании вы все равно можете использовать старый метод. В следующих разделах подробно описано, как создавать и включать файлы переопределения, а также настраивать файловую систему.

Создать файлы переопределения

Вы можете сгенерировать выровненные двоичные файлы /system/etc/fs_config_dirs и /system/etc/fs_config_files с помощью инструмента fs_config_generate в build/tools/fs_config . The tool uses a libcutils library function ( fs_config_generate() ) to manage DAC requirements into a buffer and defines rules for an include file to institutionalize the DAC rules.

Для использования создайте включаемый файл в файле device/ vendor / device /android_filesystem_config.h который будет действовать как переопределение. Файл должен использовать structure fs_path_config определенную в system/core/include/private/android_filesystem_config.h со следующей инициализацией структуры для символов каталога и файла:

  • Для каталогов используйте android _device _dirs[] .
  • Для файлов используйте android _device _files[] .

Если вы не используете android_device_dirs[] и android_device_files[] , вы можете определить NO_ANDROID_FILESYSTEM_CONFIG_DEVICE_DIRS и NO_ANDROID_FILESYSTEM_CONFIG_DEVICE_FILES (см. пример ниже). Вы также можете указать файл переопределения, используя TARGET_ANDROID_FILESYSTEM_CONFIG_H в конфигурации платы, с обязательным базовым именем android_filesystem_config.h .

Включить файлы переопределения

To include files, ensure that PRODUCT_PACKAGES includes fs_config_dirs and/or fs_config_files so it can install them to /system/etc/fs_config_dirs and /system/etc/fs_config_files , respectively. Система сборки ищет пользовательский android_filesystem_config.h в $(TARGET_DEVICE_DIR) , где существует BoardConfig.mk . Если этот файл существует где-то еще, установите переменную конфигурации платы TARGET_ANDROID_FILESYSTEM_CONFIG_H чтобы она указывала на это место.

Настройте файловую систему

Чтобы настроить файловую систему в Android 6.0 и выше:

  1. Создайте файл $(TARGET_DEVICE_DIR)/android_filesystem_config.h .
  2. Add the fs_config_dirs and/or fs_config_files to PRODUCT_PACKAGES in the board configuration file (eg, $(TARGET_DEVICE_DIR)/device.mk ).

Пример переопределения

В этом примере показан патч для переопределения демона system/bin/glgps для добавления поддержки блокировки пробуждения в каталоге device/ vendor / device . Имейте в виду следующее:

  • Каждая запись структуры содержит режим, uid, gid, возможности и имя. system/core/include/private/android_filesystem_config.h включается автоматически для предоставления #defines манифеста ( AID_ROOT , AID_SHELL , CAP_BLOCK_SUSPEND ).
  • Раздел android_device_files[] включает действие для подавления доступа к system/etc/fs_config_dirs , если оно не указано, что служит дополнительной защитой DAC от отсутствия содержимого для переопределения каталога. Однако это слабая защита; если кто-то контролирует /system , он обычно может делать все, что захочет.
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 file system
+** 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)

Мигрировать файловые системы из более ранних выпусков

При переносе файловых систем с Android 5.x и более ранних версий имейте в виду, что Android 6.x

  • Удаляет некоторые включения, структуры и встроенные определения.
  • Требуется ссылка на libcutils вместо запуска непосредственно из system/core/include/private/android_filesystem_config.h . Производитель устройства частные исполняемые файлы, которые зависят от system/code/include/private_filesystem_config.h для структур файла или каталога или fs_config , должны добавить зависимости библиотеки libcutils .
  • Requires device manufacturer private branch copies of the system/core/include/private/android_filesystem_config.h with extra content on existing targets to move to device/ vendor / device /android_filesystem_config.h .
  • Оставляет за собой право применять обязательный контроль доступа (MAC) SELinux к файлам конфигурации в целевой системе; реализации, включающие пользовательские целевые исполняемые файлы с использованием fs_config() должны обеспечивать доступ.