تقدّم هذه الصفحة طريقة أساسية لإضافة سمات النظام أو تحديدها في Android، مع إرشادات لإعادة صياغة سمات النظام الحالية. احرص على استخدام الإرشادات عند إعادة التشكيل، ما لم تكن لديك مشكلة توافق قوية تفرض خلاف ذلك.
الخطوة 1: تحديد سمة النظام
عند إضافة سمة نظام، حدِّد اسمًا للسمة واربطه بسياق سمة SELinux. إذا لم يكن هناك سياق حالي مناسب، أنشئ سياقًا جديدًا. يتم استخدام الاسم عند الوصول إلى السمة، ويتم استخدام سياق السمة للتحكّم في إمكانية الوصول من حيث SELinux. يمكن أن تكون الأسماء أي سلسلة، ولكن ننصح في AOSP باتّباع تنسيق منظَّم لجعلها واضحة.
اسم الموقع
استخدِم هذا التنسيق مع ترميز snake_case:
[{prefix}.]{group}[.{subgroup}]*.{name}[.{type}]
استخدِم "" (تم حذفها) أو ro
(للسمات التي يتم ضبطها مرة واحدة فقط) أو persist
(للسمات التي تظل محفوظة بعد عمليات إعادة التشغيل) للعنصر prefix
.
المحاذير
لا تستخدِم ro
إلا عندما تكون متأكدًا من أنّك لن تحتاج إلى prefix
ليكون قابلاً للكتابة
في المستقبل. ** لا تحدِّد بادئة ro
.** بدلاً من ذلك، يمكنك الاعتماد على سياسة الأمان ل
جعل prefix
للقراءة فقط (بمعنى آخر، يمكن لـ init
فقط الكتابة فيها).
لا تستخدِم persist
إلا عندما تكون متأكّدًا من أنّه يجب الاحتفاظ بالقيمة على الرغم من
عمليات إعادة التشغيل، وأنّ استخدام سمات النظام هو خيارك الوحيد.
تراجع Google بدقة سمات النظام التي تحتوي على سمات ro
أو persist
.
يُستخدَم مصطلح group
لتجميع المواقع ذات الصلة. ومن المفترض أن يكون
اسم نظام فرعي مشابهًا في الاستخدام لـ audio
أو telephony
. تجنَّب استخدام عبارات غامضة أو ذات معانٍ متعددة، مثل sys
أو system
أو dev
أو default
أو
config
.
من الشائع استخدام اسم نوع النطاق لسلسلة معالجة تملك إذن وصول حصري للقراءة أو الكتابة إلى سمات النظام. على سبيل المثال، بالنسبة إلى سمات النظام التي تملك عملية vold
إذن الوصول للكتابة إليها،
من الشائع استخدام vold
(اسم نوع النطاق للعملية) باسم
المجموعة.
أضِف subgroup
إذا لزم الأمر لتصنيف المواقع بشكل أكبر، ولكن تجنَّب استخدام عبارات
غامضة أو مُركّزة على مواضيع متعددة لوصف هذا العنصر. (يمكنك أيضًا استخدام أكثر
من subgroup
واحد).
سبق أن تم تحديد العديد من أسماء المجموعات. راجِع ملف
system/sepolicy/private/property_contexts
واستخدِم أسماء المجموعات الحالية
حيثما أمكن، بدلاً من إنشاء أسماء جديدة. يقدّم الجدول التالي
أمثلة على أسماء المجموعات المستخدَمة بشكلٍ متكرّر.
النطاق | المجموعة (والمجموعة الفرعية) |
---|---|
مشاكل متعلقة بالبلوتوث | bluetooth |
sysprops من سطر أوامر kernel | boot |
سمات sysprops التي تحدِّد إصدارًا | build
|
ذات صلة بالاتصالات الهاتفية | telephony |
محتوى صوتي | audio |
ذات صلة بالرسومات | graphics |
محتوى متعلّق بـ vold | vold |
يحدِّد ما يلي استخدام name
وtype
في مثال التعبير العادي السابق.
[{prefix}.]{group}[.{subgroup}]*.{name}[.{type}]
يحدِّد
name
سمة نظام ضمن مجموعة.type
هو عنصر اختياري يوضّح نوع سمة النظام أو الغرض منها. على سبيل المثال، بدلاً من تسمية سمة sysprop باسمaudio.awesome_feature_enabled
أوaudio.awesome_feature
فقط، أعِد تسميتها باسمaudio.awesome_feature.enabled
لتعكس نوع سمة النظام والغرض منها.
ما مِن قاعدة محدّدة حول النوع الذي يجب أن يكون عليه المحتوى، ولكن إليك بعض اقتراحات الاستخدام:
-
enabled
: استخدِم هذا الخيار إذا كان النوع خاصية نظام منطقية يتم استخدامها لتفعيل ميزة أو إيقافها. config
: استخدِم هذا الرمز إذا كان الغرض هو توضيح أنّ سمة النظام لا تمثّل حالة ديناميكية للنظام، بل تمثّل قيمة تم ضبطها مسبقًا (على سبيل المثال، عنصر للقراءة فقط).List
: استخدِم هذا الخيار إذا كانت سمة النظام ذات قيمة قائمة.Timeoutmillis
: استخدِم هذه السمة إذا كانت خاصية نظام لقيمة مهلة بالوحدات المللي ثانية.
أمثلة:
persist.radio.multisim.config
drm.service.enabled
سياق الموقع
يسمح مخطّط سياق سمة SELinux الجديد بدقة أكبر وأسماء أكثر وصفية. على غرار ما يتم استخدامه لأسماء المواقع، ينصح إطار عمل AOSP باستخدام التنسيق التالي:
{group}[_{subgroup}]*_prop
يتم تعريف المصطلحات على النحو التالي:
يحمل group
وsubgroup
المعنى نفسه المحدّد في
نموذج التعبير العادي السابق. على سبيل المثال، يشير الرمز vold_config_prop
إلى
السمات التي تم ضبطها من قِبل أحد المورّدين والمخصّصة لتحديد قيمة
vendor_init
، في حين يشير الرمز vold_status_prop
أو vold_prop
فقط إلى السمات
التي تعرِض الحالة الحالية لسمة vold
.
عند تسمية سياق موقع، اختَر أسماء تعكس الاستخدام العام للمواقع. وعلى وجه الخصوص، تجنَّب الأنواع التالية من العبارات:
- العبارات التي تبدو عامة ومبهمة للغاية، مثل
sys
وsystem
وdefault
- العبارات التي تُشفّر إمكانية الاستخدام مباشرةً: مثل
exported
وapponly
ro
وpublic
وprivate
يُفضَّل استخدام vold_config_prop
بدلاً من exported_vold_prop
أو
vold_vendor_writable_prop
.
النوع
يمكن أن يكون نوع الموقع أحد الأنواع التالية كما هو موضّح في الجدول.
النوع | التعريف |
---|---|
قيمة منطقية | true أو 1 للقيمة "صحيح"، وfalse أو 0 للقيمة "خطأ" |
عدد صحيح | عدد صحيح موقَّع 64 بت |
عدد صحيح غير موقّع | عدد صحيح غير موقَّت بسعة 64 بت |
مزدوجة | عدد فاصل عائم بدقة مضاعفة |
سلسلة | أي سلسلة UTF-8 صالحة |
تعداد | يمكن أن تكون قيمها أي سلسلة UTF-8 صالحة بدون مسافات بيضاء. |
قائمة بالعناصر المذكورة أعلاه | يتم استخدام فاصلة (, ) كفاصليتم تخزين قائمة الأعداد الصحيحة [1, 2, 3] على النحو التالي: 1,2,3 |
يتم تخزين جميع المواقع كسلسلة من الأحرف. يمكنك فرض النوع من خلال
تحديده كملف property_contexts
. لمزيد من المعلومات، يُرجى الاطّلاع على property_contexts
في الخطوة 3.
الخطوة 2: تحديد مستويات تسهيل الاستخدام المطلوبة
هناك أربع وحدات ماكرو مساعدة تحدّد خاصيّة.
نوع تسهيل الاستخدام | المعنى |
---|---|
system_internal_prop |
السمات المستخدَمة في /system فقط |
system_restricted_prop |
السمات التي يتم قراءتها خارج /system ، ولكن لا يتم كتابتها |
system_vendor_config_prop |
الخصائص التي تتم قراءتها خارج /system ، ولا يكتبها سوى vendor_init |
system_public_prop |
الخصائص التي تتم قراءتها وكتابتها خارج /system |
حدِّد نطاق الوصول إلى سمات النظام بقدر الإمكان. في السابق، أدّى الوصول الواسع النطاق إلى تعطُّل التطبيقات وظهور ثغرات أمنية. ضع في اعتبارك الأسئلة التالية عند تحديد النطاق:
- هل يجب الاحتفاظ بهذه السمة الخاصة بالنظام؟ (إذا كان الأمر كذلك، ما السبب؟)
- ما هي العملية التي يجب أن يكون لديها إذن بالقراءة في هذا الموقع؟
- ما هي العملية التي يجب أن يكون لديها إذن بالكتابة في هذا الموقع؟
استخدِم الأسئلة السابقة وشجرة القرارات التالية كأدوات لتحديد نطاق مناسب للوصول.
الشكل 1: شجرة قرارات لتحديد نطاق الوصول إلى خصائص النظام
الخطوة 3: الإضافة إلى system/sepolicy
عند الوصول إلى sysprop، يتحكّم SELinux في إمكانية وصول العمليات. بعد تحديد مستوى إمكانية الوصول المطلوب، حدِّد سياقات المواقع
ضمن system/sepolicy
، بالإضافة إلى قواعد allow وneverallow إضافية
حول العمليات المسموح لها (أو غير المسموح لها) بالقراءة أو الكتابة.
أولاً، حدِّد سياق الموقع في system/sepolicy/public/property.te
ملف. إذا كانت السمة داخلية للنظام، حدِّدها في ملف
system/sepolicy/private/property.te
. استخدِم إحدى system_[accessibility]_prop([context])
الوحدات النمطية التي توفّر إمكانية الوصول المطلوبة لسمة النظام. في ما يلي مثال على ملف
system/sepolicy/public/property.te
:
system_public_prop(audio_foo_prop)
system_vendor_config_prop(audio_bar_prop)
مثال على إضافة ملف system/sepolicy/private/property.te
:
system_internal_prop(audio_baz_prop)
ثانيًا، عليك منح إذن الوصول للقراءة و (أو) الكتابة إلى سياق الموقع. استخدِم وحدات الماكرو set_prop
وget_prop
لمنح إذن الوصول، سواء في ملف
system/sepolicy/public/{domain}.te
أو system/sepolicy/private/{domain}.te
. استخدِم private
كلما أمكن، ولا تستخدِم public
إلا إذا كان الماكرو
set_prop
أو get_prop
يؤثر في أي نطاقات خارج النطاق الأساسي.
على سبيل المثال، في ملف system/sepolicy/private/audio.te
:
set_prop(audio, audio_foo_prop)
set_prop(audio, audio_bar_prop)
على سبيل المثال، في ملف system/sepolicy/public/domain.te
:
get_prop(domain, audio_bar_prop)
ثالثًا، أضِف بعض قواعد neverallow للحدّ بشكل أكبر من إمكانية الوصول التي يتم تحديد نطاقها من خلال الماكرو. على سبيل المثال، لنفترض أنّك استخدمت
system_restricted_prop
لأنّه يجب أن تقرأ عمليات العميل
سمات النظام. إذا لم تكن جميع عمليات المورّد تتطلّب إذن الوصول للقراءة، ولم يكن
مطلوبًا إلا لمجموعة معيّنة من العمليات (مثل vendor_init
)، يمكنك منع
عمليات المورّد التي لا تحتاج إلى إذن الوصول للقراءة.
استخدِم التركيبة التالية لتقييد إذن الوصول للقراءة والكتابة:
لحظر إذن الكتابة:
neverallow [domain] [context]:property_service set;
لحظر الوصول للقراءة:
neverallow [domain] [context]:file no_rw_file_perms;
ضَع قواعد neverallow في ملف system/sepolicy/private/{domain}.te
إذا كانت قاعدة
neverallow مرتبطة بنطاق معيّن. للحصول على قواعد neverallow أوسع نطاقًا، استخدِم
نطاقات عامة مثل هذه كلما كان ذلك مناسبًا:
system/sepolicy/private/property.te
system/sepolicy/private/coredomain.te
system/sepolicy/private/domain.te
في ملف system/sepolicy/private/audio.te
، ضَع ما يلي:
neverallow {
domain -init -audio
} {audio_foo_prop audio_bar_prop}:property_service set;
في ملف system/sepolicy/private/property.te
، ضَع ما يلي:
neverallow {
domain -coredomain -vendor_init
} audio_prop:file no_rw_file_perms;
يُرجى العلم أنّ {domain -coredomain}
يسجِّل جميع عمليات المورّدين. وبالتالي، فإنّ {domain -coredomain -vendor_init}
تعني "جميع عمليات المورّدين باستثناء
vendor_init
".
أخيرًا، اربط سمة نظام بسياق الموقع. يضمن ذلك
أنّ إذن الوصول الممنوح وقواعد neverallow التي يتم تطبيقها على
سياقات المواقع يتم تطبيقها على المواقع الفعلية. لإجراء ذلك، أضِف إدخالًا إلىملفproperty_contexts
، وهو ملف يصف عملية الربط بين ملفّات
النظام وسياقات المواقع. في هذا الملف، يمكنك تحديد سمة
واحدة أو بادئة للسمات التي سيتم ربطها بسياق.
في ما يلي بنية ربط موقع إلكتروني واحد:
[property_name] u:object_r:[context_name]:s0 exact [type]
في ما يلي بنية ربط بادئة:
[property_name_prefix] u:object_r:[context_name]:s0 prefix [type]
يمكنك اختياريًا تحديد نوع الموقع، والذي يمكن أن يكون أحد الأنواع التالية:
bool
int
uint
double
enum [list of possible values...]
string
(استخدِمstring
لمواقع القوائم).
تأكَّد من أنّ كل إدخال يتضمّن نوعه المحدّد كلما أمكن، لأنّه يتم
فرض type
عند ضبط property
. يوضّح المثال التالي كيفية كتابة
تعيين:
# binds a boolean property "ro.audio.status.enabled"
# to the context "audio_foo_prop"
ro.audio.status.enabled u:object_r:audio_foo_prop:s0 exact bool
# binds a boolean property "vold.decrypt.status"
# to the context "vold_foo_prop"
# The property can only be set to one of these: on, off, unknown
vold.decrypt.status u:object_r:vold_foo_prop:s0 exact enum on off unknown
# binds any properties starting with "ro.audio.status."
# to the context "audio_bar_prop", such as
# "ro.audio.status.foo", or "ro.audio.status.bar.baz", and so on.
ro.audio.status. u:object_r:audio_bar_prop:s0 prefix
عند تعارض إدخال دقيق وإدخال بادئة، يكون للإدخال الدقيق
الأولوية. لمزيد من الأمثلة، يُرجى الاطّلاع على system/sepolicy/private/property_contexts
.
الخطوة 4: تحديد متطلبات الثبات
الاستقرار هو جانب آخر من خصائص النظام، ويختلف عن سهولة الاستخدام. يرتبط الاستقرار بما إذا كان يمكن تغيير خاصية النظام (على سبيل المثال، إعادة تسميتها أو حتى إزالتها) في المستقبل. وهذا مهم بشكلٍ خاص مع بدء استخدام أنظمة التشغيل Android على شكل وحدات. باستخدام Treble، يمكن تعديل أقسام النظام والمورّد والمنتج بشكل مستقل عن بعضها. باستخدام ميزة Mainline، يتم تقسيم بعض أجزاء نظام التشغيل إلى وحدات قابلة للتحديث (في حِزم APEX أو حِزم APK).
إذا كانت سمة النظام مخصّصة للاستخدام في أجزاء من البرامج قابلة للتحديث، على سبيل المثال على مستوى أقسام النظام والبائع، يجب أن تكون ثابتة. ومع ذلك، إذا كان يتم استخدامه فقط ضمن وحدة Mainline معيّنة، على سبيل المثال، يمكنك تغيير اسمه أو نوعه أو سياقات المواقع، وحتى إزالته.
اطرح الأسئلة التالية لتحديد مدى ثبات سمة النظام:
- هل يُفترَض أن يضبط الشركاء خاصية النظام هذه (أو يتم ضبطها بشكل مختلف لكل جهاز)؟ إذا كان الأمر كذلك، يجب أن يكون الاتصال ثابتًا.
- هل هذه السمة التي حدّدها نظام التشغيل AOSP مخصّصة للكتابة إلى رمز (وليس عملية) أو القراءة منه (وليس عملية) في أقسام غير نظامية مثل
vendor.img
أوproduct.img
؟ إذا كان الأمر كذلك، يجب أن يكون الاتصال ثابتًا. - هل يتم الوصول إلى سمة النظام هذه من خلال وحدات Mainline أو من خلال ملف برمجي في Mainline والجزء غير القابل للتحديث من النظام الأساسي؟ إذا كان الأمر كذلك، يجب أن يكون الاتصال ثابتًا.
بالنسبة إلى سمات النظام الثابتة، حدِّد كل سمة رسميًا كواجهة برمجة تطبيقات واستخدِم واجهة برمجة التطبيقات للوصول إلى سمة النظام، كما هو موضّح في الخطوة 6.
الخطوة 5: ضبط السمات في وقت التصميم
يمكنك ضبط الخصائص في وقت الإنشاء باستخدام متغيّرات ملف makefile. من الناحية الفنية، يتم تضمين القيم
في {partition}/build.prop
. بعد ذلك، يقرأ init
{partition}/build.prop
لضبط السمات. هناك مجموعتان من هذه
المتغيّرات: PRODUCT_{PARTITION}_PROPERTIES
وTARGET_{PARTITION}_PROP
.
يحتوي PRODUCT_{PARTITION}_PROPERTIES
على قائمة بقيم السمات. تكون البنية
{prop}={value}
أو {prop}?={value}
.
{prop}={value}
هي عملية تخصيص عادية تضمن ضبط {prop}
على
{value}
، ولا يمكن إجراء عملية تخصيص واحدة فقط من هذا النوع لكل خاصية فردية.
{prop}?={value}
هو تعيين اختياري، ويتم ضبط {prop}
على {value}
فقط في حال
عدم تعيين أي قيم {prop}={value}
. إذا كانت هناك عدة مهام اختيارية
متوفّرة، يتم استخدام المهمة الأولى.
# sets persist.traced.enable to 1 with system/build.prop
PRODUCT_SYSTEM_PROPERTIES += persist.traced.enable=1
# sets ro.zygote to zygote32 with system/build.prop
# but only when there are no other assignments to ro.zygote
# optional are useful when giving a default value to a property
PRODUCT_SYSTEM_PROPERTIES += ro.zygote?=zygote32
# sets ro.config.low_ram to true with vendor/build.prop
PRODUCT_VENDOR_PROPERTIES += ro.config.low_ram=true
يحتوي TARGET_{PARTITION}_PROP
على قائمة بالملفات التي يتم بثها مباشرةً إلى
{partition}/build.prop
. يحتوي كل ملف على قائمة بأزواج {prop}={value}
.
# example.prop
ro.cp_system_other_odex=0
ro.adb.secure=0
ro.control_privapp_permissions=disable
# emits example.prop to system/build.prop
TARGET_SYSTEM_PROP += example.prop
لمزيد من التفاصيل، يُرجى الاطّلاع على
build/make/core/sysprop.mk
.
الخطوة 6: الوصول إلى المواقع في وقت التشغيل
يمكن قراءة السمات وكتابتها أثناء التشغيل.
النصوص البرمجية لبدء التشغيل
يمكن لملفات النصوص البرمجية لبدء التشغيل (عادةً ملفات *.rc) قراءة خاصيّة باستخدام ${prop}
أو
${prop:-default}
، ويمكنها ضبط إجراء يتم تنفيذه عندما تصبح الخاصيّة قيمة
معيّنة، ويمكنها كتابة السمات باستخدام الأمر setprop
.
# when persist.device_config.global_settings.sys_traced becomes 1,
# set persist.traced.enable to 1
on property:persist.device_config.global_settings.sys_traced=1
setprop persist.traced.enable 1
# when security.perf_harden becomes 0,
# write /proc/sys/kernel/sample_rate to the value of
# debug.sample_rate. If it's empty, write -100000 instead
on property:security.perf_harden=0
write /proc/sys/kernel/sample_rate ${debug.sample_rate:-100000}
أوامر shell getprop وsetprop
يمكنك استخدام أوامر shell getprop
أو setprop
، على التوالي، لقراءة السمات أو
كتابتها. لمزيد من التفاصيل، يمكنك استدعاء getprop --help
أو
setprop --help
.
$ adb shell getprop ro.vndk.version
$
$ adb shell setprop security.perf_harden 0
Sysprop كواجهة برمجة تطبيقات لـ C++/Java/Rust
باستخدام sysprop كواجهة برمجة تطبيقات، يمكنك تحديد سمات النظام واستخدام واجهة برمجة تطبيقات تم إنشاؤها تلقائيًا
والتي تكون محدّدة وذات أنواع محدّدة. يؤدي ضبط scope
باستخدام Public
أيضًا إلى إتاحة
واجهات برمجة التطبيقات التي تم إنشاؤها للوحدات على مستوى الحدود، ويضمن ثبات واجهة برمجة التطبيقات. في ما يلي مثال على
ملف .sysprop
ووحدة Android.bp
ورمز C++ وJava وRust
يستخدمها.
# AudioProps.sysprop
# module becomes static class (Java) / namespace (C++) for serving API
module: "android.sysprop.AudioProps"
# owner can be Platform or Vendor or Odm
owner: Platform
# one prop defines one property
prop {
prop_name: "ro.audio.volume.level"
type: Integer
scope: Public
access: ReadWrite
api_name: "volume_level"
}
…
// Android.bp
sysprop_library {
name: "AudioProps",
srcs: ["android/sysprop/AudioProps.sysprop"],
property_owner: "Platform",
}
// Rust, Java and C++ modules can link against the sysprop_library
rust_binary {
rustlibs: ["libaudioprops_rust"],
…
}
java_library {
static_libs: ["AudioProps"],
…
}
cc_binary {
static_libs: ["libAudioProps"],
…
}
// Rust code accessing generated API.
// Get volume. Use 50 as the default value.
let vol = audioprops::volume_level()?.unwrap_or_else(50);
// Java codes accessing generated API
// get volume. use 50 as the default value.
int vol = android.sysprop.AudioProps.volume_level().orElse(50);
// add 10 to the volume level.
android.sysprop.AudioProps.volume_level(vol + 10);
// C++ codes accessing generated API
// get volume. use 50 as the default value.
int vol = android::sysprop::AudioProps::volume_level().value_or(50);
// add 10 to the volume level.
android::sysprop::AudioProps::volume_level(vol + 10);
لمزيد من المعلومات، يُرجى الاطّلاع على تنفيذ سمات النظام كواجهات برمجة تطبيقات.
وظائف وطرق المستوى المنخفض للخصائص في C/C++ وJava وRust
استخدِم Sysprop كواجهة برمجة تطبيقات كلما أمكن، حتى إذا كانت وظائف C/C++ أو Rust أو طرق Java ذات المستوى المنخفض متاحة لك.
يوفّر libc
وlibbase
وlibcutils
وظائف سمات النظام في C++. تحتوي دالة libc
على واجهة برمجة التطبيقات الأساسية، في حين أنّ دالتَي libbase
وlibcutils
هما دالتَا ملف ملتف. استخدِم دوال sysprop libbase
إن أمكن، فهي
الأكثر ملاءمةً، ويمكن للبرامج الثنائيّة للمضيف استخدام دوال libbase
. لمزيد من
التفاصيل، اطّلِع على sys/system_properties.h
(libc
) وandroid-base/properties.h
(libbase
) وcutils/properties.h
(libcutils
).
تقدّم فئة android.os.SystemProperties
طرقًا لسمات نظام Java.
توفّر وحدة rustutils::system_properties
وظائف
وأنواع سمات نظام Rust.
الملحق: إضافة سمات خاصة بالمورّد
يريد الشركاء (بما في ذلك موظفي Google الذين يعملون في سياق تطوير هواتف Pixel)
تحديد خصائص النظام الخاصة بالأجهزة (أو بالأجهزة).
الخصائص الخاصة بالمورّدين هي خصائص يملكها الشركاء وتكون فريدة لجهازهم أو معدّاتهم الخاصة، وليس للمنصة. وبما أنّ هذه الإعدادات تعتمد على الجهاز أو الأجهزة، فإنّها مخصّصة للاستخدام ضمن قسمَي /vendor
أو /odm
.
منذ إطلاق Project Treble، تم تقسيم خصائص النظام الأساسي وخصائص المورّد بالكامل لمنع تعارضها. يوضّح ما يلي كيفية تحديد سمات المورّد، ويشير إلى سمات المورّد التي يجب استخدامها دائمًا.
مساحة الاسم في أسماء المواقع السياقية
يجب أن تبدأ جميع سمات المورّدين بإحدى البادئات التالية لمنع حدوث تعارض بينها وبين سمات الأقسام الأخرى.
ctl.odm.
ctl.vendor.
ctl.start$odm.
ctl.start$vendor.
ctl.stop$odm.
ctl.stop$vendor.
init.svc.odm.
init.svc.vendor.
ro.odm.
ro.vendor.
odm.
persist.odm.
persist.vendor.
vendor.
يُرجى العِلم أنّه يُسمح باستخدام ro.hardware.
كبادئة، ولكن للتوافق فقط.
ولا تستخدِمها للمواقع العادية.
تستخدم جميع الأمثلة التالية إحدى البادئات المدرَجة سابقًا:
vendor.display.primary_red
persist.vendor.faceauth.use_disk_cache
ro.odm.hardware.platform
يجب أن تبدأ جميع سياقات مواقع المورّدين بـ vendor_
. ويُعدّ ذلك مفيدًا أيضًا من أجل
التوافق. في ما يلي بعض الأمثلة:
vendor_radio_prop
.vendor_faceauth_prop
.vendor_usb_prop
.
تقع على عاتق المورّد مسؤولية تسمية المواقع وصيانتها، لذا اتّبِع التنسيق المقترَح في الخطوة 2، بالإضافة إلى متطلبات مساحات أسماء المورّدين.
قواعد SEPolicy الخاصة بالمورّد وproperty_contexts
يمكن تحديد سمات المورّد باستخدام وحدة الماكرو vendor_internal_prop
. ضَع
القواعد الخاصة بالمورّد التي تحدّدها في الدليل BOARD_VENDOR_SEPOLICY_DIRS
.
على سبيل المثال، لنفترض أنّك تحدِّد خاصية faceauth الخاصة بالبائع في Coral.
في ملف BoardConfig.mk
(أو في أي ملف يتضمّن BoardConfig.mk
)، أضِف ما يلي:
BOARD_VENDOR_SEPOLICY_DIRS := device/google/coral-sepolicy
في ملف device/google/coral-sepolicy/private/property.te
، أدخِل
ما يلي:
vendor_internal_prop(vendor_faceauth_prop)
في ملف device/google/coral-sepolicy/private/property_contexts
، أدخِل
ما يلي:
vendor.faceauth.trace u:object_r:vendor_faceauth_prop:s0 exact bool
القيود المفروضة على مواقع المورّدين
بما أنّ أقسام النظام والمنتج لا يمكن أن تعتمد على المورّد، يجب عدم
السماح بالوصول إلى مواقع المورّد من أقسام system
أو system-ext
أو
product
.
الملحق: إعادة تسمية المواقع الإلكترونية الحالية
عندما يكون عليك إيقاف موقع نهائيًا والانتقال إلى موقع جديد، استخدِم Sysprop كواجهات برمجة تطبيقات
لإعادة تسمية مواقعك الحالية. يحافظ ذلك على التوافق مع الإصدارات القديمة من خلال تحديد كل من الاسم القديم واسم الموقع الجديد. وعلى وجه التحديد، يمكنك
ضبط الاسم القديم باستخدام حقل legacy_prop_name
في ملف .sysprop
. تحاول واجهة برمجة التطبيقات
المُنشأة قراءة prop_name
، وتستخدم legacy_prop_name
إذا
لم تكن prop_name
متوفّرة.
على سبيل المثال، تؤدي الخطوات التالية إلى إعادة تسمية awesome_feature_foo_enabled
إلى foo.awesome_feature.enabled
.
في ملف foo.sysprop
module: "android.sysprop.foo"
owner: Platform
prop {
api_name: "is_awesome_feature_enabled"
type: Boolean
scope: Public
access: Readonly
prop_name: "foo.awesome_feature.enabled"
legacy_prop_name: "awesome_feature_foo_enabled"
}
في رمز C++
// is_awesome_feature_enabled() reads "foo.awesome_feature.enabled".
// If it doesn't exist, reads "awesome_feature_foo_enabled" instead
using android::sysprop::foo;
bool enabled = foo::is_awesome_feature_enabled().value_or(false);
يُرجى مراعاة التحذيرات التالية:
أولاً، لا يمكنك تغيير نوع sysprop. على سبيل المثال، لا يمكنك تحويل مادة عرض
int
إلى مادة عرضstring
. يمكنك تغيير الاسم فقط.ثانيًا، لا تعود واجهة برمجة التطبيقات للقراءة إلا إلى الاسم القديم. لا يتم استخدام واجهة برمجة التطبيقات للكتابة بدلاً من واجهة برمجة التطبيقات للقراءة. إذا كان sysprop قابلاً للكتابة، لا يمكنك إعادة تسميته.