[lxc-devel] Question on freezer.c

richard -rw- weinberger richard.weinberger at gmail.com
Mon Oct 11 14:43:18 UTC 2010


On Mon, Oct 11, 2010 at 9:42 AM, Daniel Lezcano <daniel.lezcano at free.fr> wrote:
> On 10/11/2010 08:48 AM, richard -rw- weinberger wrote:
>>
>> Hi list,
>>
>> I've a question on freezer.c.
>> In freeze_unfreeze() is a while(1) loop which write()s "FROZEN" or
>> "THAWED" until read() returns the same.
>> Why do we need this loop?
>> It looks like a hack to me.
>
>
> The freezer documentation specifies:
>  state (because of the cgroup state 'freezeing), making the cgroup to
> converge to the frozen state.
>
> When we check the cgroup is frozen, the kernel look at this task list and
> find the new child process which is not yet frozen and will return
> 'freezing' instead of "frozen'. Freezing the cgroup again will freeze this
> missing task.
>
> "It's important to note that freezing can be incomplete. In that case we
> return EBUSY. This means that some tasks in the cgroup are busy doing
> something that prevents us from completely freezing the cgroup at this time.
> After EBUSY, the cgroup will remain partially frozen -- reflected by
> freezer.state reporting "FREEZING" when read. The state will remain
> "FREEZING" until one of these things happens:
>
>  1) Userspace cancels the freezing operation by writing "THAWED" to the
> freezer.state file
>
>  2) Userspace retries the freezing operation by writing "FROZEN" to the
> freezer.state file (writing "FREEZING" is not legal and returns EINVAL)
>
>  3) The tasks that blocked the cgroup from entering the "FROZEN" state
> disappear from the cgroup's set of tasks."
>
> The loop in the code is for the case (2).
>
> Let me clarify:
>
> (1) When we freeze a cgroup, the kernel browse the cgroup's tasks list and
> will send a fake signal to each of them.
>
> But the places where the hooks are in the kernel code (fork and exit), make
> possible to send this signal to a task while it is forking and the child
> process is not yet in the cgroup's task list.
>
> The forking task will go to the frozen state right after returning from the
> fork but the child task won't because it didn't receive the fake signal.
>
> If this child process forks again, the new child will automatically go to
> the frozen state (because of the cgroup state 'freezing), making the cgroup
> to converge to the frozen state.
>
> When we check the cgroup is frozen, the kernel look at this task list and
> find the new child process which is not yet frozen and will return
> 'freezing' instead of "frozen'. Freezing the cgroup again will freeze this
> missing task.
>
>
> (2) It's possible to freeze a cgroup while it is in important IO, aka
> 'uninteruptible state', so we won't be able to freeze  immediately and we
> have to retry.
>
>
>
> These both cases happen rarely, so most of the time, one iteration in the
> loop is enough to freeze the container.
>

Thanks for the clarification! :-)

-- 
Thanks,
//richard




More information about the lxc-devel mailing list