طبقة التجريد Cgroup

يستخدم Android 10 والإصدارات الأحدث طبقة تجريد لمجموعة التحكم (cgroup) مع ملفات تعريف المهام ، والتي يمكن للمطورين استخدامها لوصف مجموعة (أو مجموعات) من القيود لتطبيقها على سلسلة أو عملية. يتبع النظام بعد ذلك الإجراءات المحددة لملفات تعريف المهام لتحديد مجموعة cgroup مناسبة واحدة أو أكثر ، والتي يتم من خلالها تطبيق القيود ، ويمكن إجراء التغييرات على مجموعة ميزات cgroup الأساسية دون التأثير على طبقات البرامج الأعلى.

حول cgroups

توفر Cgroups آلية لتجميع وتقسيم مجموعات المهام (التي تتكون من العمليات والخيوط وجميع الأطفال المستقبليين) إلى مجموعات هرمية ذات سلوك متخصص. يستخدم Android cgroups للتحكم في موارد النظام وحسابها مثل استخدام وحدة المعالجة المركزية والذاكرة وتخصيصها ، مع دعم Linux kernel cgroups v1 و cgroups v2 .

Android 9 والإصدارات الأقدم

في نظام Android 9 والإصدارات الأقدم ، احتوى البرنامج النصي init.rc على مجموعة مجموعات cgroups المتاحة ونقاط التثبيت والإصدارات الخاصة بها. بينما يمكن تغيير ذلك ، توقع إطار عمل Android وجود مجموعة محددة من مجموعات cgroup في مواقع محددة بإصدار محدد وتسلسل هرمي للمجموعة الفرعية ، بناءً على البرنامج النصي. حد هذا من القدرة على اختيار إصدار cgroup التالي لاستخدامه ، أو لتغيير التسلسل الهرمي cgroup لاستخدام ميزات جديدة.

Android 10 والإصدارات الأحدث

يستخدم Android 10 والإصدارات الأحدث Cgroups مع ملفات تعريف المهام:

  • إعداد Cgroup - يصف المطورون إعداد cgroups في ملف cgroups.json الخاص بهم لتحديد مجموعات cgroups ، ومواقع التثبيت والسمات الخاصة بهم. يتم تركيب جميع مجموعات cgroups خلال مرحلة البدء المبكر لعملية التهيئة.
  • ملفات تعريف المهام - توفر فكرة تجريدية تفصل الوظيفة المطلوبة عن تفاصيل تنفيذها. يطبق إطار عمل Android ملفات تعريف المهام كما هو موضح في ملف task_profiles.json على عملية أو سلسلة رسائل باستخدام واجهات برمجة تطبيقات SetTaskProfiles و SetProcessProfiles . (واجهات برمجة التطبيقات هذه فريدة لنظام Android 11 والإصدارات الأحدث.)

لتوفير التوافق مع الإصدارات السابقة ، توفر الوظائف القديمة set_cpuset_policy و set_sched_policy و get_sched_policy نفس واجهة برمجة التطبيقات والوظائف ، ولكن تم تعديل تنفيذها لاستخدام ملفات تعريف المهام. بالنسبة لحالات الاستخدام الجديدة ، توصي AOSP باستخدام واجهات برمجة تطبيقات لملفات تعريف المهام الجديدة بدلاً من وظيفة set_sched_policy القديمة.

ملف وصف Cgroups

Cgroups موصوفة في ملف cgroups.json الموجود تحت <ANDROID_BUILD_TOP>/system/core/libprocessgroup/profiles/ . يتم وصف كل وحدة تحكم في قسم فرعي ويجب أن يكون لها حد أدنى مما يلي:

  • الاسم المحدد بواسطة حقل المراقب المالي .
  • مسار التركيب المحدد بواسطة حقل المسار .
  • الوضع ، UID (معرف المستخدم) ، و GID (معرف المجموعة) يصف المالك وأوضاع الوصول للملفات الموجودة ضمن هذا المسار (كلها اختيارية).
  • السمة الاختيارية ، مضبوطة على صواب للسماح للنظام بتجاهل خطأ التثبيت الناجم عن وحدة تحكم cgroup التي لا يدعمها kernel التثبيت.

مثال لملف cgroups.json

يوضح المثال أدناه أوصاف وحدات تحكم cgroup v1 ( Cgroups ) و cgroup v2 ( Cgroups2 ) مع مساراتها الخاصة.

{
  "Cgroups": [
    {
      "Controller": "cpu",
      "Path": "/dev/cpuctl",
      "Mode": "0755",
      "UID": "system",
      "GID": "system"
    },
    {
      "Controller": "memory",
      "Path": "/dev/memcg",
      "Mode": "0700",
      "Optional": true
    }
  ],
 "Cgroups2": {
   "Path": "/sys/fs/cgroup",
   "Mode": "0755",
   "UID": "system",
   "GID": "system",
   "Controllers": [
     {
       "Controller": "freezer",
       "Path": ".",
       "Mode": "0755",
       "UID": "system",
       "GID": "system"
     }
   ]
 }
}

يحتوي ملف المثال هذا على قسمين ، Cgroups (تصف وحدات تحكم cgroup v1) و Cgroups2 (تصف وحدات تحكم cgroup v2). يتم تثبيت جميع وحدات التحكم في التسلسل الهرمي لـ cgroups v2 في نفس الموقع. لذلك ، يحتوي قسم Cgroups2 على سمات المسار والوضع والمعرف الفريد ومعرف GID الخاص به لوصف الموقع والسمات الخاصة بجذر التسلسل الهرمي. تعتبر سمة المسار الخاصة بوحدات التحكم ضمن Cgroups2 متعلقة بمسار الجذر هذا. في Android 12 والإصدارات الأحدث ، يمكنك تعريف وحدة تحكم cgroup التي تم تحديدها بالمسار والوضع على أنها "Optional" عن طريق ضبطها على " true ".

يتم تحليل ملف cgroups.json كجزء من عملية init ، أثناء مرحلة البدء المبكر ، ويتم تثبيت مجموعات cgroups في المواقع المحددة. للحصول لاحقًا على مواقع تركيب cgroup ، استخدم دالة API CgroupGetControllerPath .

ملف ملفات تعريف المهام

يوجد ملف task_profiles.json أسفل <ANDROID_BUILD_TOP>/system/core/libprocessgroup/profiles/ . استخدمه لوصف مجموعة محددة من الإجراءات التي سيتم تطبيقها على عملية أو سلسلة رسائل. ترتبط مجموعة من الإجراءات باسم ملف التعريف ، والذي يتم استخدامه في SetTaskProfiles و SetProcessProfiles لاستدعاء إجراءات ملف التعريف.

مثال على ملف task_profiles.json

{
  "Attributes": [
    {
      "Name": "MemSoftLimit",
      "Controller": "memory",
      "File": "memory.soft_limit_in_bytes"
    },
    {
      "Name": "MemSwappiness",
      "Controller": "memory",
      "File": "memory.swappiness"
    }
  ],
  "Profiles": [
    {
      "Name": "MaxPerformance",
      "Actions" : [
        {
          "Name" : "JoinCgroup",
          "Params" :
          {
            "Controller": "schedtune",
            "Path": "top-app"
          }
        }
      ]
    },
    {
      "Name": "TimerSlackHigh",
      "Actions" : [
        {
          "Name" : "SetTimerSlack",
          "Params" :
          {
            "Slack": "40000000"
          }
        }
      ]
    },
    {
      "Name": "LowMemoryUsage",
      "Actions" : [
        {
          "Name" : "SetAttribute",
          "Params" :
          {
            "Name" : "MemSoftLimit",
            "Value" : "16MB"
          }
        },
        {
          "Name" : "SetAttribute",
          "Params" :
          {
            "Name" : "MemSwappiness",
            "Value" : "150"

          }
        }
      ]
    }
  ]
  "AggregateProfiles": [
     {
       "Name": "SCHED_SP_DEFAULT",
       "Profiles": [ "TimerSlackHigh", "MaxPerformance" ]
     },
     {
       "Name": "SCHED_SP_BACKGROUND",
       "Profiles": [ "LowMemoryUsage" ]
     }
}

قم بتعيين أسماء لملفات cgroup محددة كمدخلات في قائمة السمات . يحتوي كل إدخال على ما يلي:

  • حقل الاسم - يحدد اسم السمة.
  • حقل وحدة التحكم - يشير إلى وحدة تحكم cgroup من ملف cgroups.json ، حسب اسمها.
  • حقل الملف - يسمي ملفًا معينًا تحت وحدة التحكم هذه.

السمات هي مراجع في تعريفات ملف تعريف المهام. خارج ملفات تعريف المهام ، استخدمها فقط عندما يتطلب إطار العمل وصولاً مباشرًا إلى تلك الملفات ، ولا يمكن تلخيص الوصول باستخدام ملفات تعريف المهام. في جميع الحالات الأخرى ، استخدم ملفات تعريف المهام ؛ أنها توفر فصلًا أفضل بين السلوك المطلوب وتفاصيل تنفيذه.

يحتوي قسم ملفات التعريف على تعريفات ملفات تعريف المهام بما يلي:

  • حقل الاسم - يحدد اسم ملف التعريف.
  • قسم الإجراءات - يسرد مجموعة من الإجراءات التي تم تنفيذها عند تطبيق ملف التعريف. يحتوي كل إجراء على ما يلي:

    • حقل الاسم الذي يحدد الإجراء
    • قسم Params يحدد مجموعة من المعلمات للإجراء

يتم سرد الإجراءات المدعومة في الجدول أدناه.

عمل معامل وصف
SetTimerSlack Slack فترة سماح المؤقت في ns
SetAttribute Name اسم يشير إلى سمة من قسم السمات
Value قيمة يتم كتابتها إلى الملف ممثلة بالسمة المسماة
WriteFile FilePath مسار الملف
Value قيمة تكتب في الملف
JoinCgroup Controller اسم وحدة تحكم المجموعة من cgroups.json
Path مسار مجموعة فرعية في التسلسل الهرمي لوحدة تحكم المجموعة

يتميز Android 12 والإصدارات الأحدث بقسم AggregateProfiles الذي يحتوي على ملفات تعريف مجمعة ، كل منها عبارة عن اسم مستعار لمجموعة من ملف تعريف واحد أو أكثر. تتكون تعريفات الملف الشخصي الإجمالية مما يلي:

  • حقل الاسم - يحدد اسم ملف التعريف المجمع.
  • حقل الملفات الشخصية - يسرد أسماء الملفات الشخصية المضمنة في ملف التعريف المجمع.

عند تطبيق ملف تعريف مجمع ، يتم أيضًا تطبيق جميع ملفات التعريف المحتوية تلقائيًا. يمكن أن تحتوي ملفات التعريف المجمعة على كلٍ من ملفات التعريف الفردية أو ملفات التعريف المجمعة الأخرى ، طالما لا توجد عمليات تكرار (ملف تعريف يتضمن نفسه).

Task_profiles init لغة الأمر

يتوفر أمر task_profiles في Android Init Language لنظام Android 12 والإصدارات الأحدث لتسهيل تنشيط ملف تعريف المهمة لعملية معينة. يحل محل الأمر writepid (المهمل في Android 12) الذي تم استخدامه لترحيل عملية بين مجموعات cgroups. يوفر الأمر task_profiles مرونة لتغيير عمليات التنفيذ الأساسية دون أي تأثير على الطبقات العليا. في المثال أدناه ، يقوم هذان الأمران بتنفيذ نفس العملية بفعالية:

  • writepid /dev/cpuctl/top-app/tasks

    تم إيقافه في Android 12 - تم استخدامه لكتابة PID للمهمة الحالية في /dev/cpuctl/top-app/tasks .

  • task_profiles MaxPerformance

    ينضم إلى العملية الحالية في مجموعة التطبيقات الأعلى ضمن وحدة التحكم "cpu" ( cpuctl ) ، مما ينتج عنه كتابة PID للعملية إلى dev/cpuctl/top-app/tasks .

استخدم دائمًا الأمر task_profiles لترحيل المهام في التسلسلات الهرمية للمجموعة في Android 12 والإصدارات الأحدث. يقبل معلمة واحدة أو أكثر ، تمثل أسماء ملفات التعريف المحددة في ملف task_profiles.json .

لكل ملفات تعريف المهام على مستوى API

في Android 12 والإصدارات الأحدث ، يمكنك تعديل التعريفات أو تجاوزها في ملفات task_profiles.json و cgroups.json الافتراضية ، إما استنادًا إلى مستوى واجهة برمجة تطبيقات Android ، أو جعله من قسم البائع.

لتجاوز التعريفات بناءً على مستوى واجهة برمجة التطبيقات ، يجب أن تكون الملفات التالية موجودة على الجهاز:

  • pro/system/etc/task_profiles/cgroups_<API level>.json

    استخدم هذا لمجموعات cgroup الخاصة بمستوى API.

  • /system/etc/task_profiles/task_profiles_<API level>.json

    استخدم هذا لملفات التعريف الخاصة بمستوى API.

لإلغاء التعريفات من قسم البائع ، يجب أن تكون الملفات التالية موجودة على الجهاز:

  • /vendor/etc/cgroups.json
  • /vendor/etc/task_profiles.json

إذا كانت سمة أو تعريف ملف تعريف في هذه الملفات يستخدم نفس الاسم الموجود في الملف الافتراضي ، فإن تعريف الملف (مستوى API أو مستوى البائع) يتجاوز التعريف السابق. لاحظ أيضًا أن التعريفات على مستوى البائع تتجاوز التعريفات على مستوى واجهة برمجة التطبيقات. إذا كان للتعريف الجديد اسم جديد ، فسيتم تعديل مجموعة السمات أو ملفات التعريف بالتعريف الجديد.

يقوم نظام Android بتحميل ملفات cgroup و task_profile بالترتيب التالي:

  1. الملفات الافتراضية cgroups.json و task_profiles.json .
  2. الملفات الخاصة بمستوى API ، إن وجدت.
  3. ملفات أقسام البائع ، إن وجدت.

التغييرات على API الموجودة

يحتفظ Android 10 والإصدارات الأحدث بالوظائف set_cpuset_policy و set_sched_policy و get_sched_policy دون إجراء تغييرات على واجهة برمجة التطبيقات. ومع ذلك ، فإن Android 10 ينقل هذه الوظائف إلى libprocessgroup ، والتي تحتوي الآن على جميع الوظائف المتعلقة بـ cgroup.

على الرغم من أن رأس cutils/sched_policy.h لا يزال موجودًا ، لتجنب كسر الكود الحالي ، تأكد من أن الكود الجديد يتضمن رأس processgroup/sched_policy.h بدلاً من ذلك.

يجب أن تضيف الوحدات النمطية التي تستخدم أيًا من هذه الوظائف التبعية إلى مكتبة libprocessgroup إلى ملف makefile الخاص بها. إذا كانت الوحدة النمطية لا تستخدم أي وظائف libcutils أخرى ، فقم بإسقاط تبعية مكتبة libcutils من ملف makefile.

واجهات برمجة تطبيقات ملفات تعريف المهام

تم تحديد واجهات برمجة التطبيقات الخاصة في processgroup/processgroup.h في الجدول أدناه:

اكتب API والتعريف
bool SetTaskProfiles(int tid, const std::vector & profiles) SetTaskProfiles(int tid, const std::vector & profiles)

يطبق ملفات تعريف المهام المحددة في profiles التعريف على الخيط المحدد بواسطة معرف مؤشر الترابط (tid) باستخدام معلمة tid الخاصة به.

bool SetProcessProfiles(uid_t uid, pid_t pid, const std::vector & profiles) SetProcessProfiles(uid_t uid, pid_t pid, const std::vector & profiles)

يطبق ملفات تعريف المهام المحددة في profiles التعريف على العملية المحددة بواسطة معرفات المستخدم والعملية باستخدام معلمات uid و pid

bool CgroupGetControllerPath(const std::string& cgroup_name, std::string* path)

إرجاع ما إذا كانت وحدة تحكم cgroup المحددة بواسطة cgroup_name موجودة ؛ إذا كان هذا true ، فاضبط متغير path على جذر مجموعة المجموعة هذه

bool CgroupGetAttributePath(const std::string& attr_name, std::string* path)

إرجاع ما إذا كانت سمة ملف التعريف المحددة بواسطة attr_name موجودة ؛ إذا كان هذا true ، فاضبط متغير path على مسار الملف المرتبط بسمة ملف التعريف.

bool CgroupGetAttributePathForTask(const std::string& attr_name, int tid, std::string* path)

إرجاع ما إذا كانت سمة ملف التعريف المحددة بواسطة attr_name موجودة ؛ إذا كان هذا true ، يقوم بتعيين متغير path على مسار الملف المرتبط بسمة ملف التعريف ، وإلى الخيط المحدد بواسطة معرف مؤشر الترابط الخاص به باستخدام معلمة tid .

bool UsePerAppMemcg()

يُرجع ما إذا كان النظام قد تم تكوينه لاستخدام مجموعات مجموعات الذاكرة لكل تطبيق.