Linux Kernel Architecture

(Jacob Rumans) #1

Chapter 17: Data Synchronization


mm/backing-dev.c
long congestion_wait(int rw, long timeout)
{
long ret;
DEFINE_WAIT(wait);
wait_queue_head_t *wqh = &congestion_wqh[rw];

prepare_to_wait(wqh, &wait, TASK_UNINTERRUPTIBLE);
ret = io_schedule_timeout(timeout);
finish_wait(wqh, &wait);
return ret;
}

congestion_waitinvokes some functions once the requisite data structures have been initialized:

❑ prepare_to_waitis used in conjunction with a time out to implement waiting for clearance of
congested queues. It puts the process in theTASK_UNINTERRUPTIBLEstate and places it on the
appropriate wait queue.
❑ io_schedule_timeoutimplements the desired time out using the resources described in
Chapter 15. Control is passed to other processes until the time out expires.
Upon expiry of the time out (1 second is used for background synchronization),finish_waitis
invoked to remove the process from the wait queue so that work can continue.

17.12 Forced Writeback


The above mechanisms for writing back pages as a background activity function very well when system
load is not too high. The kernel is able to ensure that the number of dirty pages never gets out of hand and
that there is an adequate exchange of data between RAM and the underlying block devices. However, this
situation changes when the cached data of one or twoprocesses quickly become dirty, thus necessitating
more synchronization operations than can be handled by normal methods.

When the kernel receives an urgent request for memory and cannot satisfy it because of the very large
number of dirty pages, it must try to transfer the page contents to the block device as quickly as possible
to free RAM for other purposes. The same methods are used as for flushing data in the background,
but in this case, synchronization is not initiated by periodic processes but is triggered explicitly by the
kernel — in other words, writeback is ‘‘forced.’’

The request for immediate synchronization may originate not only from the kernel but also from
userspace. The familiarsynccommand (and the correspondingsyncsystem call) instructs the kernel to
flush all dirty data to the block devices. Other system calls also provided by the kernel for this purpose
are described in Section 17.14.

Synchronization is based onwakeup_pdflush, which is implemented inmm/page-writeback.c.The
number of pages to be flushed is passed as a parameter:

mm/page-writeback.c
int wakeup_pdflush(long nr_pages)
{
if (nr_pages == 0)
Free download pdf