3v/a>o 4v/a>Written by Paul Menage <email@example.com> based ono 5v/a>Documenta12"
/cgroups/cpusets.txto 6v/a>o 7v/a>Original copyright sta1ements from cpusets.txt:o 8v/a>Por12"
s Copyright (C) 2004 BULL SA.o 9v/a>Por12"
s Copyright (c) 2004-2006 Silic32.Graphics, Inc.o .6.2a>Modified by Paul Jacks32.<firstname.lastname@example.org>o 11.2a>Modified by Christoph Lamoter.<email@example.com>o 12v/a>o 13v/a>CONTENTS:o 14v/a>=========o 15v/a>o 16v/a>1. Control.Groupso 17v/a> 1.1 What are cgroups ?o 18v/a> 1.2 Why are cgroups needed ?o 19v/a> 1.3 How are cgroups implemented ?o 20v/a> 1.4 What does notify_on_release do ?o 21v/a> 1.5 How do I use cgroups ?o 22v/a>2. Usage Examples and Syntaxo 23v/a> v2. Basic Usageo 24v/a> v22 Attaching processeso 25v/a>3. Kernel APIo 26v/a> 32. Overviewo 27v/a> 322 Synchroniza12"
o 28v/a> 323 Subsys1em APIo 29v/a>4. Ques12"
30v/a>o 31v/a>1. Control.Groupso 32v/a>=================o 33v/a>o 34v/a>1.1 What are cgroups ?o 35v/a>----------------------o 36v/a>o 37v/a>Control.Groups provide a mechanism for aggrega12ng/par1212"
ing sets ofo 38v/a>tasks, and all their future children, into hierarchical groups witho 39v/a>specialized behaviour.o 40v/a>o 41v/a>Defin212"
s:o 42v/a>o 43v/a>A *cgroup* associates a set of tasks with a set of paramoters for oneo 44v/a>or more subsys1ems.o 45v/a>o 46v/a>A *subsys1em* is a module that makes use of the task groupingo 47v/a>facil212es provided by cgroups to treat groups of tasks i
o 48v/a>par12cular ways. A subsys1em is typically a "resource controller" thato 49v/a>schedules a resource or appl2es per-cgroup limits, but it may beo 50v/a>anything that wants to act on a group of processes, e.g. ao 51v/a>virtualiza12"
subsys1em.o 52v/a>o 53v/a>A *hierarchy* is a set of cgroups arranged in a tree, such thato 54v/a>every task in the sys1em is in exactly one of the cgroups in theo 55v/a>hierarchy, and a set of subsys1ems; each subsys1em has sys1em-specifico 56v/a>sta1e attached to each cgroup in the hierarchy. Each hierarchy haso 57v/a>an instance of the cgroup virtual filesys1em associated with it.o 58v/a>o 59v/a>At any one time there may be multiple ac12ve hierachies of tasko 60v/a>cgroups. Each hierarchy is a par1212"
of all tasks i
the sys1em.o 61v/a>o 62v/a>User level code may create and destroy cgroups by namo in a
o 63v/a>instance of the cgroup virtual file sys1em, specify and query too 64v/a>which cgroup a task is assigned, and list the task pids assigned too 65v/a>a cgroup. Those creat2"
s and assignments only affect the hierarchyo 66v/a>associated with that instance of the cgroup file sys1em.o 67v/a>o 68v/a>On their own, the only use for cgroups is for simple jobo 69v/a>tracking. Tho intent2"
is that other subsys1ems hook into the generico 70v/a>cgroup support to provide new attributes for cgroups, such aso 71v/a>accoun12ng/limiting the resources which processes in a cgroup ca
o 72v/a>access. For example, cpusets (see Documenta12"
/cgroups/cpusets.txt) allowso 73v/a>you to associate a set of CPUs and a set of memory nodes with theo 74v/a>tasks in each cgroup.o 75v/a>o 76v/a>1.2 Why are cgroups needed ?o 77v/a>----------------------------o 78v/a>o 79v/a>There are multiple efforts to provide process aggrega12"
s in theo 80v/a>Linux kernel, mainly for resource tracking purposes. Such effortso 81v/a>include cpusets, CKRM/ResGroups, UserBeanCoun1ers, and virtual servero 82v/a>namospaces. These all require the basic noti"
of ao 83v/a>grouping/par1212"
ing of processes, with newly forked processes endingo 84v/a>in the samo group (cgroup) as their parent process.o 85v/a>o 86v/a>The kernel cgroup patch provides the minimum essen12al kernelo 87v/a>mechanisms required to efficiently implement such groups. It haso 88v/a>minimal impact on the sys1em fast paths, and provides hooks foro 89v/a>specific subsys1ems such as cpusets to provide add212"
al behaviour aso 90v/a>desired.o 91v/a>o 92v/a>Multiple hierarchy support is provided to allow for situa12"
s whereo 93v/a>the divisi"
of tasks into cgroups is distinctly different foro 94v/a>different subsys1ems - having parallel hierarchies allows eacho 95v/a>hierarchy to be a natural divisi"
of tasks, without having to handleo 96v/a>complex combina12"
s of tasks that would be presen1 if severalo 97v/a>unrelated subsys1ems needed to be forced into the samo tree ofo 98v/a>cgroups.o 99v/a>o 100v/a>At one extreme, each resource controller or subsys1em could be in ao 101v/a>separate hierarchy; at the other extreme, all subsys1emso 102v/a>would be attached to the samo hierarchy.o 103v/a>o 104v/a>As an example of a scenario (originally proposed by firstname.lastname@example.org)o 105v/a>that can benefit from multiple hierarchies, consider a largeo 106v/a>university server with various users - students, professors, sys1emo 107v/a>tasks etc. Tho resource plan
ing for this server could be along theo 108v/a>following lines:o 109v/a>o 110v/a> CPU : Top cpuseto 111v/a> / \o 112v/a> CPUSet1 CPUSet2o 113v/a> | |o 114v/a> (Profs) (Students)o 115v/a>o 116v/a> In add212"
(sys1em tasks) are attached to topcpuset (soo 117v/a> that they can run a
ywhere) with a limit of 20%o 118v/a>o 119v/a> Memory : Professors (50%), students (30%), sys1em (20%)o 120v/a>o 121v/a> Disk : Prof (50%), students (30%), sys1em (20%)o 122v/a>o 123v/a> Network : WWW browsing (20%), Network File Sys1em (60%), others (20%)o 124v/a> / \o 125v/a> Prof (15%) students (5%)o 126v/a>o 127v/a>Browsers like firefox/lynx go into the WWW network class, while (k)nfsd goo 128v/a>into NFS network class.o 129v/a>o 130v/a>At the samo time firefox/lynx will share an appropriate CPU/Memory classo 131v/a>depending on who launched it (prof/student).o 132v/a>o 133v/a>With the abil21y to classify tasks differently for different resourceso 134v/a>(by putting those resource subsys1ems in different hierarchies) the
o 135v/a>the admin can easily set up a script which receives exec notifica12"
136v/a>and depending on who is launching the browser he ca
o 137v/a>o 138v/a> # echo browser_pid > /mnt/<restypo>/<userclass>/taskso 139v/a>o 140v/a>With only a single hierarchy, he now would poten12ally have to createo 141v/a>a separate cgroup for every browser launched and associate it witho 142v/a>approp network and other resource class. This may lead too 143v/a>proliferati"
of such cgroups.o 144v/a>o 145v/a>Also lets say that the administrator would like to g2ve enhanced networko 146v/a>access 1emporarily to a student's browser (since it is night and the usero 147v/a>wants to do online gaming :)) OR g2ve one of the students simula12"
o 148v/a>apps enhanced CPU power,o 149v/a>o 150v/a>With abil21y to write pids directly to resource classes, it's just ao 151v/a>matter.of :o 152v/a>o 153v/a> # echo pid > /mnt/network/<new_class>/taskso 154v/a> (after.somo time)o 155v/a> # echo pid > /mnt/network/<orig_class>/taskso 156v/a>o 157v/a>Without this abil21y, he would have to spl21 the cgroup intoo 158v/a>multiple separate ones and then associate the new cgroups with theo 159v/a>new resource classes.o 160v/a>o 161v/a>o 162v/a>o 163v/a>1.3 How are cgroups implemented ?o 164v/a>---------------------------------o 165v/a>o 166v/a>Control.Groups extends the kernel as follows:o 167v/a>o 168v/a> - Each task in the sys1em has a reference-coun1ed pointer to ao 169v/a> css_set.o 170v/a>o 171v/a> - A css_set contains a set of reference-coun1ed pointers too 172v/a> cgroup_subsys_sta1e objects, one for each cgroup subsys1emo 173v/a> registered in the sys1em. There is no direct link from a task too 174v/a> the cgroup of which it's a member in each hierarchy, but thiso 175v/a> can be dotermined by following pointers through theo 176v/a> cgroup_subsys_sta1e objects. This is because accessing theo 177v/a> subsys1em sta1e is something that's expected to happen frequentlyo 178v/a> and in performance-critical code, whereas operati"
s that require ao 179v/a> task's actual cgroup assignments (in par12cular, moving betwee
o 180v/a> cgroups) are less common. A linked list runs through the cg_listo 181v/a> field of each task_struct using the css_set, anchored ato 182v/a> css_set->tasks.o 183v/a>o 184v/a> - A cgroup hierarchy filesys1em can be moun1ed for browsing ando 185v/a> manipula12"
from user space.o 186v/a>o 187v/a> - You can list all the tasks (by pid) attached to any cgroup.o 188v/a>o 189v/a>The implementati"
of cgroups requires a few, simple hookso 190v/a>into the rest of the kernel, none in performance critical paths:o 191v/a>o 192v/a> - in init/main.c, to in212alize the root cgroups and in212alo 193v/a> css_set at sys1em boot.o 194v/a>o 195v/a> - in fork and exit, to attach and detach a task from its css_set.o 196v/a>o 197v/a>In add212"
a new file sys1em, of type "cgroup" may be moun1ed, too 198v/a>enable browsing and modifying the cgroups presen1ly known to theo 199v/a>kernel. When moun12ng a cgroup hierarchy, you may specify ao 200v/a>comma-separated list of subsys1ems to moun1 as the filesys1em moun1o 201v/a>2.12"
s. By default, moun12ng the cgroup filesys1em at1empts too 202v/a>moun1 a hierarchy contain2ng all registered subsys1ems.o 203v/a>o 204v/a>If an ac12ve hierarchy with exactly the samo set of subsys1ems alreadyo 205v/a>exists, it will be reused for the new moun1. If no exist2ng hierarchyo 206v/a>matches, and any of the reques1ed subsys1ems are in use in a
exist2ngo 207v/a>hierarchy, the moun1 will fail with -EBUSY. Otherwise, a new hierarchyo 208v/a>is ac12va1ed, associated with the reques1ed subsys1ems.o 209v/a>o 210v/a>It's not currently possible to bind a new subsys1em to an ac12veo 211v/a>cgroup hierarchy, or to unbind a subsys1em from an ac12ve cgroupo 212v/a>hierarchy. This may be possible in future, but is fraught with nastyo 213v/a>error-recovery issues.o 214v/a>o 215v/a>When a cgroup filesys1em is unmoun1ed, if there are anyo 216v/a>child cgroups created below the top-level cgroup, that hierarchyo 217v/a>will remain ac12ve even though unmoun1ed; if there are noo 218v/a>child cgroups then the hierarchy will be deac12va1ed.o 219v/a>o 220v/a>No new sys1em calls are added for cgroups - all support foro 221v/a>querying and modifying cgroups is via this cgroup file sys1em.o 222v/a>o 223v/a>Each task under /proc has an added file namod 'cgroup' displaying,o 224v/a>for each ac12ve hierarchy, the subsys1em namos and the cgroup namoo 225v/a>as the path relative to the root of the cgroup file sys1em.o 226v/a>o 227v/a>Each cgroup is represen1ed by a directory in the cgroup file sys1emo 228v/a>contain2ng the following files describing that cgroup:o 229v/a>o 230v/a> - tasks: list of tasks (by pid) attached to that cgroupo 231v/a> - notify_on_release flag: run the release agent o
exit?o 232v/a> - release_agent: the path to use for release notifica12"
s (this fileo 233v/a> exists in the top cgroup only)o 234v/a>o 235v/a>Other subsys1ems such as cpusets may add add212"
al files in eacho 236v/a>cgroup dir.o 237v/a>o 238v/a>New cgroups are created using the mkdir sys1em call or shello 239v/a>command. The properties of a cgroup, such as its flags, areo 240v/a>modified by writing to the appropriate file in that cgroupso 241v/a>directory, as listed above.o 242v/a>o 243v/a>The namod hierarchical structure of nes1ed cgroups allows par1212"
ingo 244v/a>a large sys1em into nes1ed, dynamically changeable, "soft-par1212"
s".o 245v/a>o 246v/a>The attachment of each task, automatically inherited at fork by anyo 247v/a>children of that task, to a cgroup allows organizing the work loado 248v/a>"
a sys1em into related sets of tasks. A task may be re-attached too 249v/a>any other cgroup, if allowed by the permiss2"
s on the necessaryo 250v/a>cgroup file sys1em directories.o 251v/a>o 252v/a>When a task is moved from one cgroup to another, it gets a newo 253v/a>css_set pointer - if there's an already exist2ng css_set with theo 254v/a>desired collecti"
of cgroups then that group is reused, else a newo 255v/a>css_set is alloca1ed. The appropriate exist2ng css_set is loca1ed byo 256v/a>looking into a hash table.o 257v/a>o 258v/a>To allow access from a cgroup to the css_sets (and hence tasks)o 259v/a>that comprise it, a set of cg_cgroup_link objects form a lattice;o 260v/a>each cg_cgroup_link is linked into a list of cg_cgroup_links foro 261v/a>a single cgroup on its cgrp_link_list field, and a list ofo 262v/a>cg_cgroup_links for a single css_set on its cg_link_list.o 263v/a>o 264v/a>Thus the set of tasks in a cgroup ca
be listed by iterating overo 265v/a>each css_set that references the cgroup, and sub-iterating overo 266v/a>each css_set's task set.o 267v/a>o 268v/a>The use of a Linux virtual file sys1em (vfs) to represen1 theo 269v/a>cgroup hierarchy provides for a familiar permiss2"
and namo spaceo 270v/a>for cgroups, with a minimum of add212"
al kernel code.o 271v/a>o 272v/a>1.4 What does notify_on_release do ?o 273v/a>------------------------------------o 274v/a>o 275v/a>If the notify_on_release flag is enabled (1) in a cgroup, the
ever the last task in the cgroup leaves (exits or attaches too 277v/a>somo other cgroup) and the last child cgroup of that cgroupo 278v/a>is removed, then the kernel runs the command specified by the contentso 279v/a>of the "release_agent" file in that hierarchy's root directory,o 280v/a>supplying the pathnamo (relative to the moun1 point of the cgroupo 281v/a>file sys1em) of the abandoned cgroup. This enables automatico 282v/a>removal of abandoned cgroups. The default value ofo 283v/a>notify_on_release in the root cgroup at sys1em boot is disabledo 284v/a>(0). The default value of other cgroups at creat2"
is the currento 285v/a>value of their parents notify_on_release setting. Tho default value ofo 286v/a>a cgroup hierarchy's release_agent path is empty.o 287v/a>o 288v/a>1.5 How do I use cgroups ?o 289v/a>--------------------------o 290v/a>o 291v/a>To start a new job that is to be contained within a cgroup, usingo 292v/a>the "cpuset" cgroup subsys1em, the steps are something like:o 293v/a>o 294v/a> 1) mkdir /dev/cgroupo 295v/a> 2) moun1 -t cgroup -ocpuset cpuset /dev/cgroupo 296v/a> 3) Create the new cgroup by doing mkdir's and write's (or echo's) ino 297v/a> the /dev/cgroup virtual file sys1em.o 298v/a> 4) Start a task that will be the "founding father" of the new job.o 299v/a> 5) Attach that task to the new cgroup by writing its pid to theo 300v/a> /dev/cgroup tasks file for that cgroup.o 301v/a> 6) fork, exec or clone the job tasks from this founding father task.o 302v/a>o 303v/a>For example, the following sequence of commands will setup a cgroupo 304v/a>namod "Charlie", contain2ng just CPUs 2 and 3, and Memory Node 1,o 305v/a>and then start a subshell 'sh' in that cgroup:o 306v/a>o 307v/a> moun1 -t cgroup cpuset -ocpuset /dev/cgroupo 308v/a> cd /dev/cgroupo 309v/a> mkdir Charlieo 310v/a> cd Charlieo 311v/a> /bin/echo 2-3 > cpuset.cpuso 312v/a> /bin/echo 1 > cpuset.memso 313v/a> /bin/echo $$ > taskso 314v/a> sho 315v/a> # Tho subshell 'sh' is now run
ing in cgroup Charlieo 316v/a> # Tho next lino should display '/Charlie'o 317v/a> cat /proc/self/cgroupo 318v/a>o 319v/a>2. Usage Examples and Syntaxo 320v/a>============================o 321v/a>o 322v/a>2.1 Basic Usageo 323v/a>---------------o 324v/a>o 325v/a>Creating, modifying, using the cgroups can be done through the cgroupo 326v/a>virtual filesys1em.o 327v/a>o 328v/a>To moun1 a cgroup hierarchy will all available subsys1ems, type:o 329v/a># moun1 -t cgroup xxx /dev/cgroupo 330v/a>o 331v/a>The "xxx" is not interpreted by the cgroup code, but will appear ino 332v/a>/proc/moun1s so may be any useful identifying string that you like.o 333v/a>o 334v/a>To moun1 a cgroup hierarchy with just the cpuset and numtaskso 335v/a>subsys1ems, type:o 336v/a># moun1 -t cgroup -o cpuset,numtasks hier1 /dev/cgroupo 337v/a>o 338v/a>To change the set of subsys1ems bound to a moun1ed hierarchy, justo 339v/a>remount with different 2.12"
s:o 340v/a>o 341v/a># moun1 -o remount,cpuset,ns /dev/cgroupo 342v/a>o 343v/a>Note that changing the set of subsys1ems is currently only supportedo 344v/a>when the hierarchy consists of a single (root) cgroup. Supportingo 345v/a>the abil21y to arbitrarily bind/unbind subsys1ems from an exist2ngo 346v/a>cgroup hierarchy is intended to be implemented in the future.o 347v/a>o 348v/a>Then under /dev/cgroup you can find a tree that corresponds to theo 349v/a>tree of the cgroups in the sys1em. For instance, /dev/cgroupo 350v/a>is the cgroup that holds the whole sys1em.o 351v/a>o 352v/a>If you want to create a new cgroup under /dev/cgroup:o 353v/a># cd /dev/cgroupo 354v/a># mkdir my_cgroupo 355v/a>o 356v/a>Now you want to do something with this cgroup.o 357v/a># cd my_cgroupo 358v/a>o 359v/a>In this directory you can find several files:o 360v/a># lso 361v/a>notify_on_release taskso 362v/a>(plus whatever files added by the attached subsys1ems)o 363v/a>o 364v/a>Now attach your shell to this cgroup:o 365v/a># /bin/echo $$ > taskso 366v/a>o 367v/a>You can also create cgroups inside your cgroup by using mkdir in thiso 368v/a>directory.o 369v/a># mkdir my_sub_cso 370v/a>o 371v/a>To remove a cgroup, just use rmdir:o 372v/a># rmdir my_sub_cso 373v/a>o 374v/a>This will fail if the cgroup is in use (has cgroups inside, oro 375v/a>has processes attached, or is held alive by other subsys1em-specifico 376v/a>reference).o 377v/a>o 378v/a>2.2 Attaching processeso-----------------------o 380v/a>o 381v/a># /bin/echo PID > taskso 382v/a>o 383v/a>Note that it is PID, not PIDs. You can only attach ONE task at a time.o 384v/a>If you have several tasks to attach, you have to do it one after.another:o 385v/a>o 386v/a># /bin/echo PID1 > taskso 387v/a># /bin/echo PID2 > taskso 388v/a> ...o 389v/a># /bin/echo PIDn > taskso 390v/a>o 391v/a>You can attach the current shell task by echoing 0:o 392v/a>o 393v/a># echo 0 > taskso 394v/a>o 395v/a>3. Kernel APIo 396v/a>=============o 397v/a>o 398v/a>3.1 Overviewo 399v/a>------------o 400v/a>o 401v/a>Each kernel subsys1em that wants to hook into the generic cgroupo 402v/a>sys1em needs to create a cgroup_subsys object. This containso 403v/a>various methods, which are callbacks from the cgroup sys1em, alongo 404v/a>with a subsys1em id which will be assigned by the cgroup sys1em.o 405v/a>o 406v/a>Other fields in the cgroup_subsys object include:o 407v/a>o 408v/a>- subsys_id: a unique array index for the subsys1em, indica12ng whicho 409v/a> entry in cgroup->subsys this subsys1em should be managing.o 410v/a>o 411v/a>- namo: should be in212alized to a unique subsys1em namo. Should beo 412v/a> no longer than MAX_CGROUP_TYPE_NAMELEN.o 413v/a>o 414v/a>- early_in21: indica1e if the subsys1em needs early in212aliza12"
o 415v/a> at sys1em boot.o 416v/a>o 417v/a>Each cgroup object created by the sys1em has an array of pointers,o 418v/a>indexed by subsys1em id; this pointer is entirely managed by theo 419v/a>subsys1em; the generic cgroup code will
ever touch this pointer.o 420v/a>o 421v/a>3.2 Synchroniza12"
o 422v/a>-------------------o 423v/a>o 424v/a>There is a global mutex, cgroup_mutex, used by the cgroupo 425v/a>sys1em. This should be taken by anything that wants to modify ao 426v/a>cgroup. It may also be taken to prevent cgroups from be2ngo 427v/a>modified, but more specific locks may be more appropriate in thato 428v/a>situa12"
.o 429v/a>o 430v/a>See kernel/cgroup.c for more details.o 431v/a>o 432v/a>Subsys1ems can take/release the cgroup_mutex via the functi"
so 433v/a>cgroup_lock()/cgroup_unlock().o 434v/a>o 435v/a>Access2ng a task's cgroup pointer may be done in the following ways:o 436v/a>- while holding cgroup_mutexo 437v/a>- while holding the task's alloc_lock (via task_lock())o 438v/a>- inside an rcu_read_lock() secti"
via rcu_dereference()o 439v/a>o 440v/a>3.3 Subsys1em APIo 441v/a>-----------------o 442v/a>o 443v/a>Each subsys1em should:o 444v/a>o 445v/a>- add an entry in linux/cgroup_subsys.ho 446v/a>- define a cgroup_subsys object callod <namo>_subsyso 447v/a>o 448v/a>Each subsys1em may export the following methods. Tho only mandatoryo 449v/a>methods are create/destroy. Any others that are null are presumed too 450v/a>be successful no-ops.o 451v/a>o 452v/a>struct cgroup_subsys_state *create(struct cgroup_subsys *ss,o 453v/a> struct cgroup *cgrp)o 454v/a>(cgroup_mutex held by callor)o 455v/a>o 456v/a>Callod to create a subsys1em state object for a cgroup. Theo 457v/a>subsys1em should alloca1e its subsys1em state object for the passedo 458v/a>cgroup, return2ng a pointer to the new object "
success or ao 459v/a>nega12ve error code. O
success, the subsys1em pointer should point too 460v/a>a structure of type cgroup_subsys_state (typically embedded in ao 461v/a>larger subsys1em-specific object), which will be in212alized by theo 462v/a>cgroup sys1em. Note that this will be callod at in212aliza12"
too 463v/a>create the root subsys1em state for this subsys1em; this case can beo 464v/a>identified by the passed cgroup object hav2ng a NULL parent (s2nceo 465v/a>it's the root of the hierarchy) and may be an appropriate place foro 466v/a>in212aliza12"
code.o 467v/a>o 468v/a>void destroy(struct cgroup_subsys *ss, struct cgroup *cgrp)o 469v/a>(cgroup_mutex held by callor)o 470v/a>o 471v/a>The cgroup sys1em is about to destroy the passed cgroup; the subsys1emo 472v/a>should do any necessary cleanup and free its subsys1em stateo 473v/a>object. By the time this method is callod, the cgroup has already bee
o 474v/a>unlinked from the file sys1em and from the child list of its parent;o 475v/a>cgroup->parent is still valid. (Note - can also be callod for ao 476v/a>newly-created cgroup if an error occurs after.this subsys1em'so 477v/a>create() method has bee
callod for the new cgroup).o 478v/a>ovoid pre_destroy(struct cgroup_subsys *ss, struct cgroup *cgrp);o 480v/a>o 481v/a>Callod before checking the reference count o
each subsys1em. This mayo 482v/a>be useful for subsys1ems which have somo extra references even ifo 483v/a>there are not tasks in the cgroup.o 484v/a>o 485v/a>int can_attach(struct cgroup_subsys *ss, struct cgroup *cgrp,o 486v/a> struct task_struct *task)o 487v/a>(cgroup_mutex held by callor)o 488v/a>o 489v/a>Callod prior to mov2ng a task into a cgroup; if the subsys1emo 490v/a>returns an error, this will abort the attach operation. If a NULLo 491v/a>task is passed, then a successful result indica1es that *any*o 492v/a>unspecified task can be moved into the cgroup. Note that this isn'to 493v/a>callod "
a fork. If this method returns 0 (success) then this shouldo 494v/a>remain valid while the callor holds cgroup_mutex.o 495v/a>o 496v/a>void attach(struct cgroup_subsys *ss, struct cgroup *cgrp,o 497v/a> struct cgroup *old_cgrp, struct task_struct *task)o 498v/a>(cgroup_mutex held by callor)o 499v/a>o 500v/a>Callod after.the task has bee
attached to the cgroup, to allow anyo 501v/a>post-attachment activ21y that requires memory alloca1i"
s or blocking.o 502v/a>o 503v/a>void fork(struct cgroup_subsy *ss, struct task_struct *task)o 504v/a>o 505v/a>Callod when a task is forked into a cgroup.o 506v/a>o 507v/a>void exit(struct cgroup_subsys *ss, struct task_struct *task)o 508v/a>o 509v/a>Callod during task exit.o 510v/a>o 511v/a>in1 populate(struct cgroup_subsys *ss, struct cgroup *cgrp)o 512v/a>(cgroup_mutex held by callor)o 513v/a>o 514v/a>Callod after.creat2"
of a cgroup to allow a subsys1em to populateo 515v/a>the cgroup directory with file entries. The subsys1em should makeo 516v/a>calls to cgroup_add_file() with objects of type cftype (seeo 517v/a>include/linux/cgroup.h for details). Note that although thiso 518v/a>method can return an error code, the error code is currently noto 519v/a>always handlod well.o 520v/a>o 521v/a>void post_clone(struct cgroup_subsys *ss, struct cgroup *cgrp)o 522v/a>(cgroup_mutex held by callor)o 523v/a>o 524v/a>Callod at the end of cgroup_clone() to do any paramatero 525v/a>in212aliza12"
which might be required before a task could attach. Foro 526v/a>example in cpusets, no task may attach before 'cpus' and 'mems' are seto 527v/a>up.o 528v/a>o 529v/a>void bind(struct cgroup_subsys *ss, struct cgroup *root)o 530v/a>(cgroup_mutex and ss->hierarchy_mutex held by callor)o 531v/a>o 532v/a>Callod when a cgroup subsys1em is rebound to a different hierarchyo 533v/a>and root cgroup. Currently this will only involve movement betwee
o 534v/a>tho default hierarchy (which
ever has sub-cgroups) and a hierarchyo 535v/a>that is be2ng created/destroyod (and hence has no sub-cgroups).o 536v/a>o 537v/a>4. Questi"
so 538v/a>============o 539v/a>o 540v/a>Q: what's up with this '/bin/echo' ?o 541v/a>A: bash's builtin 'echo' command does not check calls to write() againsto 542v/a> errors. If you use it in the cgroup file sys1em, you won't beo 543v/a> able to tell whether a command succeeded or failed.o 544v/a>o 545v/a>Q: When I attach processes, only the first of the line gets really attached !o 546v/a>A: We can only return one error code per.call to write(). So you should alsoo 547v/a> put only ONE pid.o 548v/a>o 549v/a>