linux/fs/ext4/fsync.c
<<
>>
Prefs
   1/*
   2 *  linux/fs/ext4/fsync.c
   3 *
   4 *  Copyright (C) 1993  Stephen Tweedie (sct@redhat.com)
   5 *  from
   6 *  Copyright (C) 1992  Remy Card (card@masi.ibp.fr)
   7 *                      Laboratoire MASI - Institut Blaise Pascal
   8 *                      Universite Pierre et Marie Curie (Paris VI)
   9 *  from
  10 *  linux/fs/minix/truncate.c   Copyright (C) 1991, 1992  Linus Torvalds
  11 *
  12 *  ext4fs fsync primitive
  13 *
  14 *  Big-endian to little-endian byte-swapping/bitmaps by
  15 *        David S. Miller (davem@caip.rutgers.edu), 1995
  16 *
  17 *  Removed unnecessary code duplication for little endian machines
  18 *  and excessive __inline__s.
  19 *        Andi Kleen, 1997
  20 *
  21 * Major simplications and cleanup - we only need to do the metadata, because
  22 * we can depend on generic_block_fdatasync() to sync the data blocks.
  23 */
  24
  25#include <linux/time.h>
  26#include <linux/fs.h>
  27#include <linux/sched.h>
  28#include <linux/writeback.h>
  29#include <linux/jbd2.h>
  30#include <linux/blkdev.h>
  31
  32#include "ext4.h"
  33#include "ext4_jbd2.h"
  34
  35#include <trace/events/ext4.h>
  36
  37static void dump_completed_IO(struct inode * inode)
  38{
  39#ifdef  EXT4FS_DEBUG
  40        struct list_head *cur, *before, *after;
  41        ext4_io_end_t *io, *io0, *io1;
  42        unsigned long flags;
  43
  44        if (list_empty(&EXT4_I(inode)->i_completed_io_list)){
  45                ext4_debug("inode %lu completed_io list is empty\n", inode->i_ino);
  46                return;
  47        }
  48
  49        ext4_debug("Dump inode %lu completed_io list \n", inode->i_ino);
  50        spin_lock_irqsave(&EXT4_I(inode)->i_completed_io_lock, flags);
  51        list_for_each_entry(io, &EXT4_I(inode)->i_completed_io_list, list){
  52                cur = &io->list;
  53                before = cur->prev;
  54                io0 = container_of(before, ext4_io_end_t, list);
  55                after = cur->next;
  56                io1 = container_of(after, ext4_io_end_t, list);
  57
  58                ext4_debug("io 0x%p from inode %lu,prev 0x%p,next 0x%p\n",
  59                            io, inode->i_ino, io0, io1);
  60        }
  61        spin_unlock_irqrestore(&EXT4_I(inode)->i_completed_io_lock, flags);
  62#endif
  63}
  64
  65/*
  66 * This function is called from ext4_sync_file().
  67 *
  68 * When IO is completed, the work to convert unwritten extents to
  69 * written is queued on workqueue but may not get immediately
  70 * scheduled. When fsync is called, we need to ensure the
  71 * conversion is complete before fsync returns.
  72 * The inode keeps track of a list of pending/completed IO that
  73 * might needs to do the conversion. This function walks through
  74 * the list and convert the related unwritten extents for completed IO
  75 * to written.
  76 * The function return the number of pending IOs on success.
  77 */
  78int ext4_flush_completed_IO(struct inode *inode)
  79{
  80        ext4_io_end_t *io;
  81        struct ext4_inode_info *ei = EXT4_I(inode);
  82        unsigned long flags;
  83        int ret = 0;
  84        int ret2 = 0;
  85
  86        dump_completed_IO(inode);
  87        spin_lock_irqsave(&ei->i_completed_io_lock, flags);
  88        while (!list_empty(&ei->i_completed_io_list)){
  89                io = list_entry(ei->i_completed_io_list.next,
  90                                ext4_io_end_t, list);
  91                list_del_init(&io->list);
  92                io->flag |= EXT4_IO_END_IN_FSYNC;
  93                /*
  94                 * Calling ext4_end_io_nolock() to convert completed
  95                 * IO to written.
  96                 *
  97                 * When ext4_sync_file() is called, run_queue() may already
  98                 * about to flush the work corresponding to this io structure.
  99                 * It will be upset if it founds the io structure related
 100                 * to the work-to-be schedule is fre3d.
  11
  99 *  ext4fs f03 is f IO that
 * When IO is com10ne" name=0"L13">  13/*

 * When IO is com10ndian to 0little-endian byte-swapp05 is fompleted
          David S.0 Miller (davem@caip.rutg06 is fwritten.
  16list);
  61        spin_lock_irqsave(&ei->i_completed_io_l10ary code 0duplication for little e08 is f="L57">  57
  90  86        i_completed_io_l10 class="c0omment"> *  and excessiv09 is f_io_list)){


i1name="L9">>   9next,
i_completed_io_l1ate.c   Coppyright (C) 1991, 1992  Le is 1ref">list);
  87        spin_lock_irqsave(&ei->i_completed_io_l1ine" name=="L11">  11list);
  92                = ~="+code=io" class="sref">io->flag |=  *  ext4fs ffsync11D_IN_FSYNC#endif
  13ret = ef="fs/ext4/fsyext4/fsync.c#L61" id="L61" class="line" name="L61">  61        spin_lock_irqsave(&ei->a href="fs/ext4/1indian to  little-endian byte-swappping/11ref">list6" id="
  84    1  David S.. Miller (davem@caip.rutggers.1du), 1#endif
  16list);
1n class="ccomment"> *  and excessivve __1nline__s.
 * When IO is com1 *        A1ndi K1een, 1997
  oid parf=" direcshly cs="n c) sinc2" class="line" name="L12">  12  20 *
  2, leavL94"c hug2" class="line" name="L12">  12  11);
ch"c crashan cllos  70nte" cu.50  23shly cs="n c00        /fsync.c#1L24" id="L24" class="lin1e" na12leted IO
lin1x/time">  36< */
  90int ext4_flush_completed_IO(struct i1ef="inclu1de/linux/fs.h" class="fr1ef">l1nux/fs/a>->linu12="L57">  57  2esultrold_IO(struct"L28">  2esultrol"L57"f="+code=ext4_f"bcd_IO(struct"bcflag |= lin1ux/wr129"L57">  57               dref="+codf">ext4_flush_comd9               dref="+codf="a href="fs/ext4NULL               NULLflag |= lin13XT4FS_DEBUG
ext4_flush_comss="sref">after = 1ude/linux1/blkdev.h" class="fref">1linux13ref">list>;
  83  1/fsync.c#1L31" id="L31" class="lin1e" na1e="L31line" name="L83">  83  1/span classs="comment"> *  ext4fs fse da13ref">flagsf href="fs/ext4/fsy 90  _completed_IO" c 90  _">  86        ei  83  1/ne" name=xt4_jbd2.h" class="fref"1>ext413sref">prev;
  83  1/fsync.c#1L34" id="L34" class="lin1e" na13ref">listref="fs/ext4/fslush_completed_IO" class="sref="a href="fs/ext4igrabcompleted_IO" clgrab">  86        dump_complete1events/ex1t4.h" class="fref">trace1/even13="L85">  85  _completed_IO" c 90  _">  86        ei< /a>->list);
  _completed_IO" c 90  _">  86        ei" class="sref">dump_complete1elude/lin1   57
  86        dump_complete1eux/write138" id="L38" class="line1" nam13_io_list)){

               dref="+cod  83  1href="+co1de=EXT4FS_DEBUG" class="1sref"14sref">next,
dump_complete1ore, 1*list);
after =   86                       dref="+codve" class="sref">spid=parf="e" name="L90"> d=parf="a>inve" class="sref">spid= href="+code=dump_cod= hrefed_IO" class="sref">dump_complete1ef">io0, *list);
 dpu"">  86                       dref="+codO" class="sref">dump_complete1espan clas ;

after =   83  1hne" name=""L13">  13prev;
dump_complete1ofsync.c#1_list" class="sref">i_co1mplet1d_io_list)){
 ipu"">  86        dump_complete1->1i_ino);
after = 1class="li1ne" name="L46">  46 1     147ef">list);
  86        spin_m" name&dump_complete114="L57">  57

  83  1hux/write1L48" id="L48" class="lin1e" na14n",
dump_complete1->1next,
(struct"bcflag, 0, sizeof(struct"bcflag)O" class="sref">dump_complete1ock, 1list);
(struct"bcflagi->_ALL               WB_ef">_ALLa href="+code=cur" class="sref">1_list1, list){
(struct"bcflagi->after r_to_"L28"" class=">){

list;
  86        (struct"bcflagO" class="sref">dump_complete1one" name=gt;prev;

  83  1end_t1, list);
dump_complete1->1gt;next#endif
inode);
 ipu"">  86        dump_complete1/fsync.c#1L57" id="L57" class="lin1e" na1e="L57">  57i_completed_io_l1ode %1lu,prev 0x%p,next 0x1%1\n&quo#endif
io0, #endif
1631858bc8e33f6_3/0">1ock, 11oio-&1d="L62" class="line" nam1e="L616 blocks.
 " d="L93" class="line" name="L93">1one" name=63" id="L63" class="line1" nam16 through
1ond_t1L64" id="L64" class="lin1e" na1e="L64">  64
  65/*
  70" n"ync.s/a> * When IO is com1ine" name1="L67">  67 *
        pleted, t1he work to convert unwri1tten 1xtents to
  36< */
ext4_flush_completed_IO(struct 
  83  1led. When1 fsync is called, we nee1d to 1nsure /a>->list */
" cllass="sref">i_completed_io_l1eps track1 of a list of pending/co1mplet17ref">flags;
i_completed_io_l1ene" name=conversion. This functio1n wal17"L63">  63}
listref="fs/ext4/fs/fsync.c#L83" id="L83" classc.c#L90" id="L9lass=m" name_bufferode=i_completed_lass=m" name_buffero">  86        spin_m" name&dump_complete175">  75<1/a> * t17sref">next
        spin_">  _completed_IO" ci8">  _">  <   ei  83  1ion retur1n the number of pending 1IOs o177ef">list);
i_completed_io_l1ne" name=1"L77">  77next

        spin_">  _completed_IO" ci8">  _">  <   ei  83  1ileted, t1*,
i_completed_io_l1fsync.c#L179" id="L79" class="line1" nam18sref"/a>#endif
after;
" classc.c#L90" id="L9lass= href_  86        dump_complete1T4_I(1inodea>
i1gned long1 list;
 = " cllass="sref">i_completed_io_l1      int1 ret = 6" id="a href="fs/ext4/fsync.c#L83" id="L83" cllass="sref">i_completed_io_l1f the rel1a href="+code=ret2" clas1s="sr1f">ret#endif
>
1ock, 1 *
        pleted_io1_list" class="sref">i_co1mplet18tents to
  18.
  18 *
        io-&g1t;
 *  Big-eIO_END_IN1_FSYNC" class="sref">EXT14_IO_19 blocks.
  _fsy=84/fjoid=a""L94"system00        i     int1               /*
  18
 * schedu1lass="com1ment">                 *1 IO t1 written.
        i_IO(1span class="comment">   1     1        *
  18, 1le() is called, run_queu1e() m1y already
  18 *  and excessiveplet1tructure.
#endif
inf">ext4_flush_com"lin = in                  2""ine" name="L90">  2""ina>infc.c#L90" id="L9ltarne" name="L90"> ltarna>in                  2""ine" name="L90">  2""ina>infc.c#L90" id="L9en0" id="L40" clasen0ref=,< */
  83  20ne" name20"L11">  11-> *  ext4fs 203 is20sref">listext4_flush_completed_IO(struct ins="line" name="L92"> _m" name&hoist_del_init(hois" cllass="sref">i_completed_io_l20ne" name20"L13">  13list  81        struct ext4_inode_info *ei = EX20ndian to20little-endian byte-swap205 is20ref">listref="fs/ext4/fsjoid=a"ine" name="L90"> joid=a"in 81        structjoid=a"e" name="L90"> joid=a"4_inode_info" class="sref">SBxt4_inode_info *SB">  86        spin_sbcompleted_IO" cl_sbef="+ve" class="sref">spis_joid=a"e" name="L90"> s_joid=a"" cllass="sref">i_completed_io_l20nclude/li0 Miller (davem@caip.rut206 is20sref">nexti_completed_io_l20ne" name20"L16">  16inode);
 tilina>infc.c#L90" id="L9 hreic_tile" name="L90">  hreic_til" cllass="sref">i_completed_io_l20lude/linu0duplication for little 208 is2f="L57">  57ref=assc.c#L90" id="L9"alsn = i_completed_io_l20ux/writeb0omment"> *  and excessi209 is2f_io_lass="sref">i_completed_io_l2name="L9"2>   9  79{
  86          8)a== 6        EX2ate.c   C2ppyright (C) 1991, 1992 2Le is21lkdev.h>
  11list);
 tme="_"fs/elass="lin_9nter">  86        in                 line" na               dine" na" clEX2aspan cla2ss="comment"> *  ext4fs 2fsync21ref">flags;
  13ret = ef="fs/ext4/fsy/fsync.c#L83" id="L83" classc.c#L90" id="L9ch_rm" _"L28"_c#L_waic_rangn =   86        spin_m" name& ltarna>in                 en0" id="L40" clasen0ref=EX2andian to2 little-endian byte-swap2ping/21ref">lista>
  83  2  David S2. Miller (davem@caip.rut2gers.21ef">i_ino);
i_completed_io_l2ine" name2="L16">  16inode);
(">  81                href="+code=dump_completed_Ive" class="sref">spin_mutex&EX2alude/linu duplication for little 2endia2147        }
 *  and excessi2ve __219ef">lista>
spin_sbcompleted_IO" cl_sbef="ve" class="sref">spis_="+code=i_completed_s_="+co">  <     83  2 *        A2ndi K22sref">next,
 ou3" cllass="sref">i_completed_io_l2ine" name2="L20">  20  11list);
  78intf="+code=ei" class="sref">ei = EX2neric_blo2ck_fdatasync() to sync t2he da22ref">flagsf h);

i2nne" name2"L23">  23prev;
 ou3" cllass="sref">i_completed_io_l2indian to2L24" id="L24" class="lin2e" na22">ret2 = 0;
lin22sref">next
        structjoid=a"e" name="L90"> joid=a"4_in< /a>->l227ef">list);
int6        EX2clude/lin2ux/sched.h" class="fref"2>linu22="L57">  57

        struct/fsync.c#L83" id="L83" cla>  hnc.c#L88" id="L88" class=h"line" name="L88">  88        w href="+code=dump_completed_Ive" class="sref">spin_d9               n_d9f">ei  83  2nux/write2back.h" class="fref">lin2ux/wr22n",
  90intf="+code=ei" class="sref">ei = EX2include/l2inux/jbd2.h" class="fref2">lin23sref">next,
 ou3" cllass="sref">i_completed_io_l2ude/linux2/blkdev.h" class="fref">2linux23ref">list#endif
  83  2/span cla2ss="comment"> *  ext4fs 2se da23ref">flags
2/ne" name2xt4_jbd2.h" class="fref"2>ext423ment">/*
  2,ordered: id="L93" class="line" name="L93">2/ndian to2L34" id="L34" class="lin2e" na23ompleted
       2events/ex2t4.h" class="fref">trace2/even23written.
 * When IO is com2/fsync.c#2L36" id="L36" class="lin2e" na23       *
       2elude/lin2 
2/ux/write238" id="L38" class="line2" nam23ructure.
2href="+co2de=EXT4FS_DEBUG" class="2sref"24lated
  18, 2*
                 * It wil2ef">io0, *
  18
  18  13/*
(olaanass="line" name="L18">  18i_co2mplet24ompleted
 lass="line" name="L18">  18  46 2     247ef">list>f h);
intf="+code=ei" class="sref">ei = 24="L57">  57
  86        spin_sbcompleted_IO" cl_sbef="+lass="sref">i_completed_io_l2hux/write2L48" id="L48" class="lin2e" na24n",
 ou3" cllass="sref">i_completed_io_l2->2next#endif
2, list);
  hreic_til" clf="a href="fs/ext4dine" na               dine" na" clspin_dine" na_tile" name="L90"> n_dine" na_til" cl<:ea href="fs/ext4="+code=spin_lock_irqsave" class="sref">spin_" na_tile" name="L90"> n_" na_til" cllass="sref">i_completed_io_l2flagsf h);
 joid=a"4_inve" class="sref">spij_="+code=i_completed_j_="+co">  <     i_completed_io_l2prev;
        structjbd2_id=ns_"L99_ss="ldine_barria> =   86         joid=a"4_ini<                hreic_tile" name="L90">  hreic_til" cli  83  2end_t2, list);
ref=assc.c#L90" id="L9tru"e" name="L90"> tmun" cllass="sref">i_completed_io_l2->2gt;  85
  86         joid=a"4_ini<                hreic_tile" name="L90">  hreic_til" clilass="sref">i_completed_io_l2inode);
  86         joid=a"4_ini<                hreic_tile" name="L90">  hreic_til" clilass="sref">i_completed_io_l2next

 =   83  2eux/write2lu,prev 0x%p,next 0x2%25_io_list)){
(structblkdev_issue" name">  86        spin_sbcompleted_IO" cl_sbef="ve" class="sref">spis_bdevde=i_completed_s_bdev4_ini<               GFP_KERNEL               GFP_KERNEL4_ini<               NULL               NULLflag+code=EXT4_I" class="sref">EX2ef">io0,  ou3" cl:ode=EXT4_I" class="sref">EX2eck, 2L60" class="line" name="2L60">26ref">after;
  81                href="+code=dump_completed_Ive" class="sref">spin_mutex&EX2ock, 2list);
EX2ospan cla2d="L62" class="line" nam2e="L626ref">flagsi_completed_io_l2one" name263" id="L63" class="line2" nam26 thro#endif



"/div>

lxr@4" ux.noe="L.
"/div>
RedpL99 L" pro ASe="L,