27 Dec, 2011

1 commit


09 Dec, 2011

1 commit

  • At present, the functions freezer_count() and freezer_do_not_count()
    impose the restriction that they are effective only for userspace processes.
    However, now, these functions have found more utility than originally
    intended by the commit which introduced it: ba96a0c8 (freezer:
    fix vfork problem). And moreover, even the vfork issue actually does not
    need the above restriction in these functions.

    So, modify these functions to make them work even for kernel threads, so
    that they can be used at other places in the kernel, where the userspace
    restriction doesn't apply.

    Suggested-by: Oleg Nesterov
    Suggested-by: Tejun Heo
    Acked-by: Tejun Heo
    Reviewed-by: Oleg Nesterov
    Signed-off-by: Srivatsa S. Bhat
    Signed-off-by: Rafael J. Wysocki

    Srivatsa S. Bhat
     

07 Dec, 2011

1 commit

  • Allow the freezer to skip wait_on_bit_killable sleeps in the sunrpc
    layer. This should allow suspend and hibernate events to proceed, even
    when there are RPC's pending on the wire.

    Also, wrap the TASK_KILLABLE sleeps in NFS layer in freezer_do_not_count
    and freezer_count calls. This allows the freezer to skip tasks that are
    sleeping while looping on EJUKEBOX or NFS4ERR_DELAY sorts of errors.

    Signed-off-by: Jeff Layton
    Signed-off-by: Rafael J. Wysocki

    Jeff Layton
     

25 Nov, 2011

1 commit


24 Nov, 2011

2 commits

  • wait_event_freezable() and friends stop the waiting if try_to_freeze()
    fails. This is not right, we can race with __thaw_task() and in this
    case

    - wait_event_freezable() returns the wrong ERESTARTSYS

    - wait_event_freezable_timeout() can return the positive
    value while condition == F

    Change the code to always check __retval/condition before return.

    Note: with or without this patch the timeout logic looks strange,
    probably we should recalc timeout if try_to_freeze() returns T.

    Signed-off-by: Oleg Nesterov
    Acked-by: Tejun Heo

    Oleg Nesterov
     
  • There's no in-kernel user of set_freezable_with_signal() left. Mixing
    TIF_SIGPENDING with kernel threads can lead to nasty corner cases as
    kernel threads never travel signal delivery path on their own.

    e.g. the current implementation is buggy in the cancelation path of
    __thaw_task(). It calls recalc_sigpending_and_wake() in an attempt to
    clear TIF_SIGPENDING but the function never clears it regardless of
    sigpending state. This means that signallable freezable kthreads may
    continue executing with !freezing() && stuck TIF_SIGPENDING, which can
    be troublesome.

    This patch removes set_freezable_with_signal() along with
    PF_FREEZER_NOSIG and recalc_sigpending*() calls in freezer. User
    tasks get TIF_SIGPENDING, kernel tasks get woken up and the spurious
    sigpending is dealt with in the usual signal delivery path.

    Signed-off-by: Tejun Heo
    Acked-by: Oleg Nesterov

    Tejun Heo
     

22 Nov, 2011

9 commits

  • After "freezer: make freezing() test freeze conditions in effect
    instead of TIF_FREEZE", freezing() returns authoritative answer on
    whether the current task should freeze or not and freeze_task()
    doesn't need or use @sig_only. Remove it.

    While at it, rewrite function comment for freeze_task() and rename
    @sig_only to @user_only in try_to_freeze_tasks().

    This patch doesn't cause any functional change.

    Signed-off-by: Tejun Heo
    Acked-by: Oleg Nesterov

    Tejun Heo
     
  • A kthread doing set_freezable*() may race with on-going PM freeze and
    the freezer might think all tasks are frozen while the new freezable
    kthread is merrily proceeding to execute code paths which aren't
    supposed to be executing during PM freeze.

    Reimplement set_freezable[_with_signal]() using __set_freezable() such
    that freezable PF flags are modified under freezer_lock and
    try_to_freeze() is called afterwards. This eliminates race condition
    against freezing.

    Note: Separated out from larger patch to resolve fix order dependency
    Oleg pointed out.

    Signed-off-by: Tejun Heo
    Cc: Oleg Nesterov

    Tejun Heo
     
  • should_send_signal() is only used in freezer.c. Exporting them only
    increases chance of abuse. Open code the two users and remove it.

    Update frozen() to return bool.

    Signed-off-by: Tejun Heo

    Tejun Heo
     
  • Using TIF_FREEZE for freezing worked when there was only single
    freezing condition (the PM one); however, now there is also the
    cgroup_freezer and single bit flag is getting clumsy.
    thaw_processes() is already testing whether cgroup freezing in in
    effect to avoid thawing tasks which were frozen by both PM and cgroup
    freezers.

    This is racy (nothing prevents race against cgroup freezing) and
    fragile. A much simpler way is to test actual freeze conditions from
    freezing() - ie. directly test whether PM or cgroup freezing is in
    effect.

    This patch adds variables to indicate whether and what type of
    freezing conditions are in effect and reimplements freezing() such
    that it directly tests whether any of the two freezing conditions is
    active and the task should freeze. On fast path, freezing() is still
    very cheap - it only tests system_freezing_cnt.

    This makes the clumsy dancing aroung TIF_FREEZE unnecessary and
    freeze/thaw operations more usual - updating state variables for the
    new state and nudging target tasks so that they notice the new state
    and comply. As long as the nudging happens after state update, it's
    race-free.

    * This allows use of freezing() in freeze_task(). Replace the open
    coded tests with freezing().

    * p != current test is added to warning printing conditions in
    try_to_freeze_tasks() failure path. This is necessary as freezing()
    is now true for the task which initiated freezing too.

    -v2: Oleg pointed out that re-freezing FROZEN cgroup could increment
    system_freezing_cnt. Fixed.

    Signed-off-by: Tejun Heo
    Acked-by: Paul Menage (for the cgroup portions)

    Tejun Heo
     
  • TIF_FREEZE will be removed soon and freezing() will directly test
    whether any freezing condition is in effect. Make the following
    changes in preparation.

    * Rename cgroup_freezing_or_frozen() to cgroup_freezing() and make it
    return bool.

    * Make cgroup_freezing() access task_freezer() under rcu read lock
    instead of task_lock(). This makes the state dereferencing racy
    against task moving to another cgroup; however, it was already racy
    without this change as ->state dereference wasn't synchronized.
    This will be later dealt with using attach hooks.

    * freezer->state is now set before trying to push tasks into the
    target state.

    -v2: Oleg pointed out that freeze_change_state() was setting
    freeze->state incorrectly to CGROUP_FROZEN instead of
    CGROUP_FREEZING. Fixed.

    -v3: Matt pointed out that setting CGROUP_FROZEN used to always invoke
    try_to_freeze_cgroup() regardless of the current state. Patch
    updated such that the actual freeze/thaw operations are always
    performed on invocation. This shouldn't make any difference
    unless something is broken.

    Signed-off-by: Tejun Heo
    Acked-by: Paul Menage
    Cc: Li Zefan
    Cc: Oleg Nesterov

    Tejun Heo
     
  • freeze_processes() failure path is rather messy. Freezing is canceled
    for workqueues and tasks which aren't frozen yet but frozen tasks are
    left alone and should be thawed by the caller and of course some
    callers (xen and kexec) didn't do it.

    This patch updates __thaw_task() to handle cancelation correctly and
    makes freeze_processes() and freeze_kernel_threads() call
    thaw_processes() on failure instead so that the system is fully thawed
    on failure. Unnecessary [suspend_]thaw_processes() calls are removed
    from kernel/power/hibernate.c, suspend.c and user.c.

    While at it, restructure error checking if clause in suspend_prepare()
    to be less weird.

    -v2: Srivatsa spotted missing removal of suspend_thaw_processes() in
    suspend_prepare() and error in commit message. Updated.

    Signed-off-by: Tejun Heo
    Acked-by: Srivatsa S. Bhat

    Tejun Heo
     
  • thaw_process() now has only internal users - system and cgroup
    freezers. Remove the unnecessary return value, rename, unexport and
    collapse __thaw_process() into it. This will help further updates to
    the freezer code.

    -v3: oom_kill grew a use of thaw_process() while this patch was
    pending. Convert it to use __thaw_task() for now. In the longer
    term, this should be handled by allowing tasks to die if killed
    even if it's frozen.

    -v2: minor style update as suggested by Matt.

    Signed-off-by: Tejun Heo
    Cc: Paul Menage
    Cc: Matt Helsley

    Tejun Heo
     
  • Writeback and thinkpad_acpi have been using thaw_process() to prevent
    deadlock between the freezer and kthread_stop(); unfortunately, this
    is inherently racy - nothing prevents freezing from happening between
    thaw_process() and kthread_stop().

    This patch implements kthread_freezable_should_stop() which enters
    refrigerator if necessary but is guaranteed to return if
    kthread_stop() is invoked. Both thaw_process() users are converted to
    use the new function.

    Note that this deadlock condition exists for many of freezable
    kthreads. They need to be converted to use the new should_stop or
    freezable workqueue.

    Tested with synthetic test case.

    Signed-off-by: Tejun Heo
    Acked-by: Henrique de Moraes Holschuh
    Cc: Jens Axboe
    Cc: Oleg Nesterov

    Tejun Heo
     
  • There is no reason to export two functions for entering the
    refrigerator. Calling refrigerator() instead of try_to_freeze()
    doesn't save anything noticeable or removes any race condition.

    * Rename refrigerator() to __refrigerator() and make it return bool
    indicating whether it scheduled out for freezing.

    * Update try_to_freeze() to return bool and relay the return value of
    __refrigerator() if freezing().

    * Convert all refrigerator() users to try_to_freeze().

    * Update documentation accordingly.

    * While at it, add might_sleep() to try_to_freeze().

    Signed-off-by: Tejun Heo
    Cc: Samuel Ortiz
    Cc: Chris Mason
    Cc: "Theodore Ts'o"
    Cc: Steven Whitehouse
    Cc: Andrew Morton
    Cc: Jan Kara
    Cc: KONISHI Ryusuke
    Cc: Christoph Hellwig

    Tejun Heo
     

05 Nov, 2011

1 commit

  • Commit 27920651fe "PM / Freezer: Make fake_signal_wake_up() wake
    TASK_KILLABLE tasks too" updated fake_signal_wake_up() used by freezer
    to wake up KILLABLE tasks. Sending unsolicited wakeups to tasks in
    killable sleep is dangerous as there are code paths which depend on
    tasks not waking up spuriously from KILLABLE sleep.

    For example. sys_read() or page can sleep in TASK_KILLABLE assuming
    that wait/down/whatever _killable can only fail if we can not return
    to the usermode. TASK_TRACED is another obvious example.

    The offending commit was to resolve freezer hang during system PM
    operations caused by KILLABLE sleeps in network filesystems.
    wait_event_freezekillable(), which depends on the spurious KILLABLE
    wakeup, was added by f06ac72e92 "cifs, freezer: add
    wait_event_freezekillable and have cifs use it" to be used to
    implement killable & freezable sleeps in network filesystems.

    To prepare for reverting of 27920651fe, this patch reimplements
    wait_event_freezekillable() using freezer_do_not_count/freezer_count()
    so that it doesn't depend on the spurious KILLABLE wakeup. This isn't
    very nice but should do for now.

    [tj: Refreshed patch to apply to linus/master and updated commit
    description on Rafael's request.]

    Signed-off-by: Oleg Nesterov
    Signed-off-by: Tejun Heo
    Signed-off-by: Rafael J. Wysocki

    Oleg Nesterov
     

29 Oct, 2011

1 commit

  • * '3.2-without-smb2' of git://git.samba.org/sfrench/cifs-2.6: (52 commits)
    Fix build break when freezer not configured
    Add definition for share encryption
    CIFS: Make cifs_push_locks send as many locks at once as possible
    CIFS: Send as many mandatory unlock ranges at once as possible
    CIFS: Implement caching mechanism for posix brlocks
    CIFS: Implement caching mechanism for mandatory brlocks
    CIFS: Fix DFS handling in cifs_get_file_info
    CIFS: Fix error handling in cifs_readv_complete
    [CIFS] Fixup trivial checkpatch warning
    [CIFS] Show nostrictsync and noperm mount options in /proc/mounts
    cifs, freezer: add wait_event_freezekillable and have cifs use it
    cifs: allow cifs_max_pending to be readable under /sys/module/cifs/parameters
    cifs: tune bdi.ra_pages in accordance with the rsize
    cifs: allow for larger rsize= options and change defaults
    cifs: convert cifs_readpages to use async reads
    cifs: add cifs_async_readv
    cifs: fix protocol definition for READ_RSP
    cifs: add a callback function to receive the rest of the frame
    cifs: break out 3rd receive phase into separate function
    cifs: find mid earlier in receive codepath
    ...

    Linus Torvalds
     

28 Oct, 2011

1 commit

  • fs/cifs/transport.c: In function 'wait_for_response':
    fs/cifs/transport.c:328: error: implicit declaration of function 'wait_event_freezekillable'

    Caused by commit f06ac72e9291 ("cifs, freezer: add
    wait_event_freezekillable and have cifs use it"). In this config,
    CONFIG_FREEZER is not set.

    Reviewed-by: Shirish Pargaonkar
    CC: Jeff Layton
    Signed-off-by: Steve French

    Steve French
     

20 Oct, 2011

2 commits

  • Signed-off-by: Steve French

    Steve French
     
  • CIFS currently uses wait_event_killable to put tasks to sleep while
    they await replies from the server. That function though does not
    allow the freezer to run. In many cases, the network interface may
    be going down anyway, in which case the reply will never come. The
    client then ends up blocking the computer from suspending.

    Fix this by adding a new wait_event_freezable variant --
    wait_event_freezekillable. The idea is to combine the behavior of
    wait_event_killable and wait_event_freezable -- put the task to
    sleep and only allow it to be awoken by fatal signals, but also
    allow the freezer to do its job.

    Signed-off-by: Jeff Layton

    Jeff Layton
     

17 Oct, 2011

1 commit

  • There is a problem with the current ordering of hibernate code which
    leads to deadlocks in some filesystems' memory shrinkers. Namely,
    some filesystems use freezable kernel threads that are inactive when
    the hibernate memory preallocation is carried out. Those same
    filesystems use memory shrinkers that may be triggered by the
    hibernate memory preallocation. If those memory shrinkers wait for
    the frozen kernel threads, the hibernate process deadlocks (this
    happens with XFS, for one example).

    Apparently, it is not technically viable to redesign the filesystems
    in question to avoid the situation described above, so the only
    possible solution of this issue is to defer the freezing of kernel
    threads until the hibernate memory preallocation is done, which is
    implemented by this change.

    Unfortunately, this requires the memory preallocation to be done
    before the "prepare" stage of device freeze, so after this change the
    only way drivers can allocate additional memory for their freeze
    routines in a clean way is to use PM notifiers.

    Reported-by: Christoph
    Signed-off-by: Rafael J. Wysocki

    Rafael J. Wysocki
     

17 Feb, 2011

1 commit

  • There are two spellings in use for 'freeze' + 'able' - 'freezable' and
    'freezeable'. The former is the more prominent one. The latter is
    mostly used by workqueue and in a few other odd places. Unify the
    spelling to 'freezable'.

    Signed-off-by: Tejun Heo
    Reported-by: Alan Stern
    Acked-by: "Rafael J. Wysocki"
    Acked-by: Greg Kroah-Hartman
    Acked-by: Dmitry Torokhov
    Cc: David Woodhouse
    Cc: Alex Dubov
    Cc: "David S. Miller"
    Cc: Steven Whitehouse

    Tejun Heo
     

27 Mar, 2010

1 commit

  • When the cgroup freezer is used to freeze tasks we do not want to thaw
    those tasks during resume. Currently we test the cgroup freezer
    state of the resuming tasks to see if the cgroup is FROZEN. If so
    then we don't thaw the task. However, the FREEZING state also indicates
    that the task should remain frozen.

    This also avoids a problem pointed out by Oren Ladaan: the freezer state
    transition from FREEZING to FROZEN is updated lazily when userspace reads
    or writes the freezer.state file in the cgroup filesystem. This means that
    resume will thaw tasks in cgroups which should be in the FROZEN state if
    there is no read/write of the freezer.state file to trigger this
    transition before suspend.

    NOTE: Another "simple" solution would be to always update the cgroup
    freezer state during resume. However it's a bad choice for several reasons:
    Updating the cgroup freezer state is somewhat expensive because it requires
    walking all the tasks in the cgroup and checking if they are each frozen.
    Worse, this could easily make resume run in N^2 time where N is the number
    of tasks in the cgroup. Finally, updating the freezer state from this code
    path requires trickier locking because of the way locks must be ordered.

    Instead of updating the freezer state we rely on the fact that lazy
    updates only manage the transition from FREEZING to FROZEN. We know that
    a cgroup with the FREEZING state may actually be FROZEN so test for that
    state too. This makes sense in the resume path even for partially-frozen
    cgroups -- those that really are FREEZING but not FROZEN.

    Reported-by: Oren Ladaan
    Signed-off-by: Matt Helsley
    Cc: stable@kernel.org
    Signed-off-by: Rafael J. Wysocki

    Matt Helsley
     

31 Oct, 2008

1 commit


20 Oct, 2008

2 commits

  • This patch implements a new freezer subsystem in the control groups
    framework. It provides a way to stop and resume execution of all tasks in
    a cgroup by writing in the cgroup filesystem.

    The freezer subsystem in the container filesystem defines a file named
    freezer.state. Writing "FROZEN" to the state file will freeze all tasks
    in the cgroup. Subsequently writing "RUNNING" will unfreeze the tasks in
    the cgroup. Reading will return the current state.

    * Examples of usage :

    # mkdir /containers/freezer
    # mount -t cgroup -ofreezer freezer /containers
    # mkdir /containers/0
    # echo $some_pid > /containers/0/tasks

    to get status of the freezer subsystem :

    # cat /containers/0/freezer.state
    RUNNING

    to freeze all tasks in the container :

    # echo FROZEN > /containers/0/freezer.state
    # cat /containers/0/freezer.state
    FREEZING
    # cat /containers/0/freezer.state
    FROZEN

    to unfreeze all tasks in the container :

    # echo RUNNING > /containers/0/freezer.state
    # cat /containers/0/freezer.state
    RUNNING

    This is the basic mechanism which should do the right thing for user space
    task in a simple scenario.

    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 "RUNNING" 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 EIO)
    3) The tasks that blocked the cgroup from entering the "FROZEN"
    state disappear from the cgroup's set of tasks.

    [akpm@linux-foundation.org: coding-style fixes]
    [akpm@linux-foundation.org: export thaw_process]
    Signed-off-by: Cedric Le Goater
    Signed-off-by: Matt Helsley
    Acked-by: Serge E. Hallyn
    Tested-by: Matt Helsley
    Signed-off-by: Andrew Morton
    Signed-off-by: Linus Torvalds

    Matt Helsley
     
  • Now that the TIF_FREEZE flag is available in all architectures, extract
    the refrigerator() and freeze_task() from kernel/power/process.c and make
    it available to all.

    The refrigerator() can now be used in a control group subsystem
    implementing a control group freezer.

    Signed-off-by: Cedric Le Goater
    Signed-off-by: Matt Helsley
    Acked-by: Serge E. Hallyn
    Tested-by: Matt Helsley
    Cc: "Rafael J. Wysocki"
    Signed-off-by: Andrew Morton
    Signed-off-by: Linus Torvalds

    Matt Helsley
     

17 Jul, 2008

1 commit

  • The freezer currently attempts to distinguish kernel threads from
    user space tasks by checking if their mm pointer is unset and it
    does not send fake signals to kernel threads. However, there are
    kernel threads, mostly related to networking, that behave like
    user space tasks and may want to be sent a fake signal to be frozen.

    Introduce the new process flag PF_FREEZER_NOSIG that will be set
    by default for all kernel threads and make the freezer only send
    fake signals to the tasks having PF_FREEZER_NOSIG unset. Provide
    the set_freezable_with_signal() function to be called by the kernel
    threads that want to be sent a fake signal for freezing.

    This patch should not change the freezer's observable behavior.

    Signed-off-by: Rafael J. Wysocki
    Signed-off-by: Andi Kleen
    Acked-by: Pavel Machek
    Signed-off-by: Len Brown

    Rafael J. Wysocki
     

19 Oct, 2007

1 commit

  • Introduce freezer-friendly wrappers around wait_event_interruptible() and
    wait_event_interruptible_timeout(), originally defined in , to
    be used in freezable kernel threads. Make some of the freezable kernel
    threads use them.

    This is necessary for the freezer to stop sending signals to kernel threads,
    which is implemented in the next patch.

    Signed-off-by: Rafael J. Wysocki
    Acked-by: Pavel Machek
    Cc: Nigel Cunningham
    Signed-off-by: Andrew Morton
    Signed-off-by: Linus Torvalds

    Rafael J. Wysocki
     

30 Jul, 2007

1 commit

  • Introduce CONFIG_SUSPEND representing the ability to enter system sleep
    states, such as the ACPI S3 state, and allow the user to choose SUSPEND
    and HIBERNATION independently of each other.

    Make HOTPLUG_CPU be selected automatically if SUSPEND or HIBERNATION has
    been chosen and the kernel is intended for SMP systems.

    Also, introduce CONFIG_PM_SLEEP which is automatically selected if
    CONFIG_SUSPEND or CONFIG_HIBERNATION is set and use it to select the
    code needed for both suspend and hibernation.

    The top-level power management headers and the ACPI code related to
    suspend and hibernation are modified to use the new definitions (the
    changes in drivers/acpi/sleep/main.c are, mostly, moving code to reduce
    the number of ifdefs).

    There are many other files in which CONFIG_PM can be replaced with
    CONFIG_PM_SLEEP or even with CONFIG_SUSPEND, but they can be updated in
    the future.

    Signed-off-by: Rafael J. Wysocki
    Signed-off-by: Linus Torvalds

    Rafael J. Wysocki
     

20 Jul, 2007

1 commit

  • Kernel threads should not have TIF_FREEZE set when user space processes are
    being frozen, since otherwise some of them might be frozen prematurely.
    To prevent this from happening we can (1) make exit_mm() unset TIF_FREEZE
    unconditionally just after clearing tsk->mm and (2) make try_to_freeze_tasks()
    check if p->mm is different from zero and PF_BORROWED_MM is unset in p->flags
    when user space processes are to be frozen.

    Namely, when user space processes are being frozen, we only should set
    TIF_FREEZE for tasks that have p->mm different from NULL and don't have
    PF_BORROWED_MM set in p->flags. For this reason task_lock() must be used to
    prevent try_to_freeze_tasks() from racing with use_mm()/unuse_mm(), in which
    p->mm and p->flags.PF_BORROWED_MM are changed under task_lock(p). Also, we
    need to prevent the following scenario from happening:

    * daemonize() is called by a task spawned from a user space code path
    * freezer checks if the task has p->mm set and the result is positive
    * task enters exit_mm() and clears its TIF_FREEZE
    * freezer sets TIF_FREEZE for the task
    * task calls try_to_freeze() and goes to the refrigerator, which is wrong at
    that point

    This requires us to acquire task_lock(p) before p->flags.PF_BORROWED_MM and
    p->mm are examined and release it after TIF_FREEZE is set for p (or it turns
    out that TIF_FREEZE should not be set).

    Signed-off-by: Rafael J. Wysocki
    Cc: Gautham R Shenoy
    Cc: Pavel Machek
    Cc: Nigel Cunningham
    Cc: Oleg Nesterov
    Signed-off-by: Andrew Morton
    Signed-off-by: Linus Torvalds

    Rafael J. Wysocki
     

18 Jul, 2007

1 commit

  • Currently, the freezer treats all tasks as freezable, except for the kernel
    threads that explicitly set the PF_NOFREEZE flag for themselves. This
    approach is problematic, since it requires every kernel thread to either
    set PF_NOFREEZE explicitly, or call try_to_freeze(), even if it doesn't
    care for the freezing of tasks at all.

    It seems better to only require the kernel threads that want to or need to
    be frozen to use some freezer-related code and to remove any
    freezer-related code from the other (nonfreezable) kernel threads, which is
    done in this patch.

    The patch causes all kernel threads to be nonfreezable by default (ie. to
    have PF_NOFREEZE set by default) and introduces the set_freezable()
    function that should be called by the freezable kernel threads in order to
    unset PF_NOFREEZE. It also makes all of the currently freezable kernel
    threads call set_freezable(), so it shouldn't cause any (intentional)
    change of behaviour to appear. Additionally, it updates documentation to
    describe the freezing of tasks more accurately.

    [akpm@linux-foundation.org: build fixes]
    Signed-off-by: Rafael J. Wysocki
    Acked-by: Nigel Cunningham
    Cc: Pavel Machek
    Cc: Oleg Nesterov
    Cc: Gautham R Shenoy
    Signed-off-by: Andrew Morton
    Signed-off-by: Linus Torvalds

    Rafael J. Wysocki
     

24 May, 2007

4 commits

  • Other than refrigerator, no one else calls frozen_process(). So move it from
    include/linux/freezer.h to kernel/power/process.c.

    Also, since a task can be marked as frozen by itself, we don't need to pass
    the (struct task_struct *p) parameter to frozen_process().

    Signed-off-by: Gautham R Shenoy
    Signed-off-by: Rafael J. Wysocki
    Cc: Oleg Nesterov
    Cc: Pavel Machek
    Cc: "Eric W. Biederman"
    Signed-off-by: Andrew Morton
    Signed-off-by: Linus Torvalds

    Gautham R Shenoy
     
  • This patch fixes the race pointed out by Oleg Nesterov.

    * Freezer marks a thread as freezeable.
    * The thread now marks itself PF_NOFREEZE, but it will be frozen on
    on calling try_to_freeze(). Thus the task is frozen, even though it doesn't
    want to.
    * Subsequent thaw_processes() will also fail to thaw the task since it is
    marked PF_NOFREEZE.

    Avoid this problem by checking the task's PF_NOFREEZE status in
    frozen_processes() before marking the task as frozen.

    Signed-off-by: Gautham R Shenoy
    Signed-off-by: Rafael J. Wysocki
    Cc: Oleg Nesterov
    Cc: Pavel Machek
    Cc: "Eric W. Biederman"
    Signed-off-by: Andrew Morton
    Signed-off-by: Linus Torvalds

    Gautham R Shenoy
     
  • Currently try_to_freeze_tasks() has to wait until all of the vforked processes
    exit and for this reason every user can make it fail. To fix this problem we
    can introduce the additional process flag PF_FREEZER_SKIP to be used by tasks
    that do not want to be counted as freezable by the freezer and want to have
    TIF_FREEZE set nevertheless. Then, this flag can be set by tasks using
    sys_vfork() before they call wait_for_completion(&vfork) and cleared after
    they have woken up. After clearing it, the tasks should call try_to_freeze()
    as soon as possible.

    Signed-off-by: Rafael J. Wysocki
    Cc: Gautham R Shenoy
    Cc: Oleg Nesterov
    Cc: Pavel Machek
    Cc: "Eric W. Biederman"
    Signed-off-by: Andrew Morton
    Signed-off-by: Linus Torvalds

    Rafael J. Wysocki
     
  • If the freezing of tasks fails and a task is preempted in refrigerator()
    before calling frozen_process(), then thaw_tasks() may run before this task is
    frozen. In that case the task will freeze and no one will thaw it.

    To fix this race we can call freezing(current) in refrigerator() along with
    frozen_process(current) under the task_lock() which also should be taken in
    the error path of try_to_freeze_tasks() as well as in thaw_process().
    Moreover, if thaw_process() additionally clears TIF_FREEZE for tasks that are
    not frozen, we can be sure that all tasks are thawed and there are no pending
    "freeze" requests after thaw_tasks() has run.

    Signed-off-by: Rafael J. Wysocki
    Acked-by: Pavel Machek
    Cc: Gautham R Shenoy
    Cc: Oleg Nesterov
    Cc: "Eric W. Biederman"
    Signed-off-by: Andrew Morton
    Signed-off-by: Linus Torvalds

    Rafael J. Wysocki
     

14 Dec, 2006

1 commit

  • Currently, to tell a task that it should go to the refrigerator, we set the
    PF_FREEZE flag for it and send a fake signal to it. Unfortunately there
    are two SMP-related problems with this approach. First, a task running on
    another CPU may be updating its flags while the freezer attempts to set
    PF_FREEZE for it and this may leave the task's flags in an inconsistent
    state. Second, there is a potential race between freeze_process() and
    refrigerator() in which freeze_process() running on one CPU is reading a
    task's PF_FREEZE flag while refrigerator() running on another CPU has just
    set PF_FROZEN for the same task and attempts to reset PF_FREEZE for it. If
    the refrigerator wins the race, freeze_process() will state that PF_FREEZE
    hasn't been set for the task and will set it unnecessarily, so the task
    will go to the refrigerator once again after it's been thawed.

    To solve first of these problems we need to stop using PF_FREEZE to tell
    tasks that they should go to the refrigerator. Instead, we can introduce a
    special TIF_*** flag and use it for this purpose, since it is allowed to
    change the other tasks' TIF_*** flags and there are special calls for it.

    To avoid the freeze_process()-refrigerator() race we can make
    freeze_process() to always check the task's PF_FROZEN flag after it's read
    its "freeze" flag. We should also make sure that refrigerator() will
    always reset the task's "freeze" flag after it's set PF_FROZEN for it.

    Signed-off-by: Rafael J. Wysocki
    Acked-by: Pavel Machek
    Cc: Russell King
    Cc: David Howells
    Cc: Andi Kleen
    Cc: "Luck, Tony"
    Cc: Benjamin Herrenschmidt
    Cc: Paul Mackerras
    Cc: Paul Mundt
    Signed-off-by: Andrew Morton
    Signed-off-by: Linus Torvalds

    Rafael J. Wysocki
     

11 Dec, 2006

1 commit

  • freezer.h uses task_struct fields so it should include sched.h.

    CC [M] fs/jfs/jfs_txnmgr.o
    In file included from fs/jfs/jfs_txnmgr.c:49:
    include/linux/freezer.h: In function 'frozen':
    include/linux/freezer.h:9: error: dereferencing pointer to incomplete type
    include/linux/freezer.h:9: error: 'PF_FROZEN' undeclared (first use in this function)
    include/linux/freezer.h:9: error: (Each undeclared identifier is reported only once
    include/linux/freezer.h:9: error: for each function it appears in.)
    include/linux/freezer.h: In function 'freezing':
    include/linux/freezer.h:17: error: dereferencing pointer to incomplete type
    include/linux/freezer.h:17: error: 'PF_FREEZE' undeclared (first use in this function)
    include/linux/freezer.h: In function 'freeze':
    include/linux/freezer.h:26: error: dereferencing pointer to incomplete type
    include/linux/freezer.h:26: error: 'PF_FREEZE' undeclared (first use in this function)
    include/linux/freezer.h: In function 'do_not_freeze':
    include/linux/freezer.h:34: error: dereferencing pointer to incomplete type
    include/linux/freezer.h:34: error: 'PF_FREEZE' undeclared (first use in this function)
    include/linux/freezer.h: In function 'thaw_process':
    include/linux/freezer.h:43: error: dereferencing pointer to incomplete type
    include/linux/freezer.h:43: error: 'PF_FROZEN' undeclared (first use in this function)
    include/linux/freezer.h:44: warning: implicit declaration of function 'wake_up_process'
    include/linux/freezer.h: In function 'frozen_process':
    include/linux/freezer.h:55: error: dereferencing pointer to incomplete type
    include/linux/freezer.h:55: error: dereferencing pointer to incomplete type
    include/linux/freezer.h:55: error: 'PF_FREEZE' undeclared (first use in this function)
    include/linux/freezer.h:55: error: 'PF_FROZEN' undeclared (first use in this function)
    fs/jfs/jfs_txnmgr.c: In function 'freezing':
    include/linux/freezer.h:18: warning: control reaches end of non-void function
    make[2]: *** [fs/jfs/jfs_txnmgr.o] Error 1

    Signed-off-by: Randy Dunlap
    Acked-by: Dave Kleikamp
    Signed-off-by: Andrew Morton
    Signed-off-by: Linus Torvalds

    Randy Dunlap
     

08 Dec, 2006

3 commits

  • Move the loop from thaw_processes() to a separate function and call it
    independently for kernel threads and user space processes so that the order
    of thawing tasks is clearly visible.

    Drop thaw_kernel_threads() which is never used.

    Signed-off-by: Rafael J. Wysocki
    Cc: Pavel Machek
    Cc: Nigel Cunningham
    Signed-off-by: Andrew Morton
    Signed-off-by: Linus Torvalds

    Rafael J. Wysocki
     
  • Modify process thawing so that we can thaw kernel space without thawing
    userspace, and thaw kernelspace first. This will be useful in later
    patches, where I intend to get swsusp thawing kernel threads only before
    seeking to free memory.

    Signed-off-by: Nigel Cunningham
    Cc: Pavel Machek
    Cc: "Rafael J. Wysocki"
    Signed-off-by: Andrew Morton
    Signed-off-by: Linus Torvalds

    Nigel Cunningham
     
  • Move process freezing functions from include/linux/sched.h to freezer.h, so
    that modifications to the freezer or the kernel configuration don't require
    recompiling just about everything.

    [akpm@osdl.org: fix ueagle driver]
    Signed-off-by: Nigel Cunningham
    Cc: "Rafael J. Wysocki"
    Cc: Pavel Machek
    Signed-off-by: Andrew Morton
    Signed-off-by: Linus Torvalds

    Nigel Cunningham