home *** CD-ROM | disk | FTP | other *** search
/ Il CD di internet / CD.iso / SOURCE / KERNEL-S / V1.2 / LINUX-1.2 / LINUX-1 / linux / fs / ext2 / inode.c < prev    next >
Encoding:
C/C++ Source or Header  |  1995-02-26  |  19.2 KB  |  669 lines

  1. /*
  2.  *  linux/fs/ext2/inode.c
  3.  *
  4.  *  Copyright (C) 1992, 1993, 1994  Remy Card (card@masi.ibp.fr)
  5.  *                                  Laboratoire MASI - Institut Blaise Pascal
  6.  *                                  Universite Pierre et Marie Curie (Paris VI)
  7.  *
  8.  *  from
  9.  *
  10.  *  linux/fs/minix/inode.c
  11.  *
  12.  *  Copyright (C) 1991, 1992  Linus Torvalds
  13.  *
  14.  *  Goal-directed block allocation by Stephen Tweedie (sct@dcs.ed.ac.uk), 1993
  15.  */
  16.  
  17. #include <asm/segment.h>
  18. #include <asm/system.h>
  19.  
  20. #include <linux/errno.h>
  21. #include <linux/fs.h>
  22. #include <linux/ext2_fs.h>
  23. #include <linux/sched.h>
  24. #include <linux/stat.h>
  25. #include <linux/string.h>
  26. #include <linux/locks.h>
  27. #include <linux/mm.h>
  28.  
  29. void ext2_put_inode (struct inode * inode)
  30. {
  31.     ext2_discard_prealloc (inode);
  32.     if (inode->i_nlink || inode->i_ino == EXT2_ACL_IDX_INO ||
  33.         inode->i_ino == EXT2_ACL_DATA_INO)
  34.         return;
  35.     inode->i_size = 0;
  36.     if (inode->i_blocks)
  37.         ext2_truncate (inode);
  38.     ext2_free_inode (inode);
  39. }
  40.  
  41. #define inode_bmap(inode, nr) ((inode)->u.ext2_i.i_data[(nr)])
  42.  
  43. static int block_bmap (struct buffer_head * bh, int nr)
  44. {
  45.     int tmp;
  46.  
  47.     if (!bh)
  48.         return 0;
  49.     tmp = ((u32 *) bh->b_data)[nr];
  50.     brelse (bh);
  51.     return tmp;
  52. }
  53.  
  54. /* 
  55.  * ext2_discard_prealloc and ext2_alloc_block are atomic wrt. the
  56.  * superblock in the same manner as are ext2_free_blocks and
  57.  * ext2_new_block.  We just wait on the super rather than locking it
  58.  * here, since ext2_new_block will do the necessary locking and we
  59.  * can't block until then.
  60.  */
  61. void ext2_discard_prealloc (struct inode * inode)
  62. {
  63. #ifdef EXT2_PREALLOCATE
  64.     if (inode->u.ext2_i.i_prealloc_count) {
  65.         int i = inode->u.ext2_i.i_prealloc_count;
  66.         inode->u.ext2_i.i_prealloc_count = 0;
  67.         ext2_free_blocks (inode->i_sb,
  68.                   inode->u.ext2_i.i_prealloc_block,
  69.                   i);
  70.     }
  71. #endif
  72. }
  73.  
  74. static int ext2_alloc_block (struct inode * inode, unsigned long goal)
  75. {
  76. #ifdef EXT2FS_DEBUG
  77.     static unsigned long alloc_hits = 0, alloc_attempts = 0;
  78. #endif
  79.     unsigned long result;
  80.     struct buffer_head * bh;
  81.  
  82.     wait_on_super (inode->i_sb);
  83.  
  84. #ifdef EXT2_PREALLOCATE
  85.     if (inode->u.ext2_i.i_prealloc_count &&
  86.         (goal == inode->u.ext2_i.i_prealloc_block ||
  87.          goal + 1 == inode->u.ext2_i.i_prealloc_block))
  88.     {        
  89.         result = inode->u.ext2_i.i_prealloc_block++;
  90.         inode->u.ext2_i.i_prealloc_count--;
  91.         ext2_debug ("preallocation hit (%lu/%lu).\n",
  92.                 ++alloc_hits, ++alloc_attempts);
  93.  
  94.         /* It doesn't matter if we block in getblk() since
  95.            we have already atomically allocated the block, and
  96.            are only clearing it now. */
  97.         if (!(bh = getblk (inode->i_sb->s_dev, result,
  98.                    inode->i_sb->s_blocksize))) {
  99.             ext2_error (inode->i_sb, "ext2_alloc_block",
  100.                     "cannot get block %lu", result);
  101.             return 0;
  102.         }
  103.         memset(bh->b_data, 0, inode->i_sb->s_blocksize);
  104.         bh->b_uptodate = 1;
  105.         mark_buffer_dirty(bh, 1);
  106.         brelse (bh);
  107.     } else {
  108.         ext2_discard_prealloc (inode);
  109.         ext2_debug ("preallocation miss (%lu/%lu).\n",
  110.                 alloc_hits, ++alloc_attempts);
  111.         if (S_ISREG(inode->i_mode))
  112.             result = ext2_new_block
  113.                 (inode->i_sb, goal,
  114.                  &inode->u.ext2_i.i_prealloc_count,
  115.                  &inode->u.ext2_i.i_prealloc_block);
  116.         else
  117.             result = ext2_new_block (inode->i_sb, goal, 0, 0);
  118.     }
  119. #else
  120.     result = ext2_new_block (inode->i_sb, goal, 0, 0);
  121. #endif
  122.  
  123.     return result;
  124. }
  125.  
  126.  
  127. int ext2_bmap (struct inode * inode, int block)
  128. {
  129.     int i;
  130.     int addr_per_block = EXT2_ADDR_PER_BLOCK(inode->i_sb);
  131.  
  132.     if (block < 0) {
  133.         ext2_warning (inode->i_sb, "ext2_bmap", "block < 0");
  134.         return 0;
  135.     }
  136.     if (block >= EXT2_NDIR_BLOCKS + addr_per_block +
  137.              addr_per_block * addr_per_block +
  138.              addr_per_block * addr_per_block * addr_per_block) {
  139.         ext2_warning (inode->i_sb, "ext2_bmap", "block > big");
  140.         return 0;
  141.     }
  142.     if (block < EXT2_NDIR_BLOCKS)
  143.         return inode_bmap (inode, block);
  144.     block -= EXT2_NDIR_BLOCKS;
  145.     if (block < addr_per_block) {
  146.         i = inode_bmap (inode, EXT2_IND_BLOCK);
  147.         if (!i)
  148.             return 0;
  149.         return block_bmap (bread (inode->i_dev, i,
  150.                       inode->i_sb->s_blocksize), block);
  151.     }
  152.     block -= addr_per_block;
  153.     if (block < addr_per_block * addr_per_block) {
  154.         i = inode_bmap (inode, EXT2_DIND_BLOCK);
  155.         if (!i)
  156.             return 0;
  157.         i = block_bmap (bread (inode->i_dev, i,
  158.                        inode->i_sb->s_blocksize),
  159.                 block / addr_per_block);
  160.         if (!i)
  161.             return 0;
  162.         return block_bmap (bread (inode->i_dev, i,
  163.                       inode->i_sb->s_blocksize),
  164.                    block & (addr_per_block - 1));
  165.     }
  166.     block -= addr_per_block * addr_per_block;
  167.     i = inode_bmap (inode, EXT2_TIND_BLOCK);
  168.     if (!i)
  169.         return 0;
  170.     i = block_bmap (bread (inode->i_dev, i, inode->i_sb->s_blocksize),
  171.             block / (addr_per_block * addr_per_block));
  172.     if (!i)
  173.         return 0;
  174.     i = block_bmap (bread (inode->i_dev, i, inode->i_sb->s_blocksize),
  175.             (block / addr_per_block) & (addr_per_block - 1));
  176.     if (!i)
  177.         return 0;
  178.     return block_bmap (bread (inode->i_dev, i, inode->i_sb->s_blocksize),
  179.                block & (addr_per_block - 1));
  180. }
  181.  
  182. static struct buffer_head * inode_getblk (struct inode * inode, int nr,
  183.                       int create, int new_block, int * err)
  184. {
  185.     u32 * p;
  186.     int tmp, goal = 0;
  187.     struct buffer_head * result;
  188.     int blocks = inode->i_sb->s_blocksize / 512;
  189.  
  190.     p = inode->u.ext2_i.i_data + nr;
  191. repeat:
  192.     tmp = *p;
  193.     if (tmp) {
  194.         result = getblk (inode->i_dev, tmp, inode->i_sb->s_blocksize);
  195.         if (tmp == *p)
  196.             return result;
  197.         brelse (result);
  198.         goto repeat;
  199.     }
  200.     if (!create || new_block >= 
  201.         (current->rlim[RLIMIT_FSIZE].rlim_cur >>
  202.          EXT2_BLOCK_SIZE_BITS(inode->i_sb))) {
  203.         *err = -EFBIG;
  204.         return NULL;
  205.     }
  206.     if (inode->u.ext2_i.i_next_alloc_block == new_block)
  207.         goal = inode->u.ext2_i.i_next_alloc_goal;
  208.  
  209.     ext2_debug ("hint = %d,", goal);
  210.  
  211.     if (!goal) {
  212.         for (tmp = nr - 1; tmp >= 0; tmp--) {
  213.             if (inode->u.ext2_i.i_data[tmp]) {
  214.                 goal = inode->u.ext2_i.i_data[tmp];
  215.                 break;
  216.             }
  217.         }
  218.         if (!goal)
  219.             goal = (inode->u.ext2_i.i_block_group * 
  220.                 EXT2_BLOCKS_PER_GROUP(inode->i_sb)) +
  221.                    inode->i_sb->u.ext2_sb.s_es->s_first_data_block;
  222.     }
  223.  
  224.     ext2_debug ("goal = %d.\n", goal);
  225.  
  226.     tmp = ext2_alloc_block (inode, goal);
  227.     if (!tmp)
  228.         return NULL;
  229.     result = getblk (inode->i_dev, tmp, inode->i_sb->s_blocksize);
  230.     if (*p) {
  231.         ext2_free_blocks (inode->i_sb, tmp, 1);
  232.         brelse (result);
  233.         goto repeat;
  234.     }
  235.     *p = tmp;
  236.     inode->u.ext2_i.i_next_alloc_block = new_block;
  237.     inode->u.ext2_i.i_next_alloc_goal = tmp;
  238.     inode->i_ctime = CURRENT_TIME;
  239.     inode->i_blocks += blocks;
  240.     if (IS_SYNC(inode) || inode->u.ext2_i.i_osync)
  241.         ext2_sync_inode (inode);
  242.     else
  243.         inode->i_dirt = 1;
  244.     return result;
  245. }
  246.  
  247. static struct buffer_head * block_getblk (struct inode * inode,
  248.                       struct buffer_head * bh, int nr,
  249.                       int create, int blocksize, 
  250.                       int new_block, int * err)
  251. {
  252.     int tmp, goal = 0;
  253.     u32 * p;
  254.     struct buffer_head * result;
  255.     int blocks = inode->i_sb->s_blocksize / 512;
  256.  
  257.     if (!bh)
  258.         return NULL;
  259.     if (!bh->b_uptodate) {
  260.         ll_rw_block (READ, 1, &bh);
  261.         wait_on_buffer (bh);
  262.         if (!bh->b_uptodate) {
  263.             brelse (bh);
  264.             return NULL;
  265.         }
  266.     }
  267.     p = (u32 *) bh->b_data + nr;
  268. repeat:
  269.     tmp = *p;
  270.     if (tmp) {
  271.         result = getblk (bh->b_dev, tmp, blocksize);
  272.         if (tmp == *p) {
  273.             brelse (bh);
  274.             return result;
  275.         }
  276.         brelse (result);
  277.         goto repeat;
  278.     }
  279.     if (!create || new_block >= 
  280.         (current->rlim[RLIMIT_FSIZE].rlim_cur >> 
  281.          EXT2_BLOCK_SIZE_BITS(inode->i_sb))) {
  282.         brelse (bh);
  283.         *err = -EFBIG;
  284.         return NULL;
  285.     }
  286.     if (inode->u.ext2_i.i_next_alloc_block == new_block)
  287.         goal = inode->u.ext2_i.i_next_alloc_goal;
  288.     if (!goal) {
  289.         for (tmp = nr - 1; tmp >= 0; tmp--) {
  290.             if (((u32 *) bh->b_data)[tmp]) {
  291.                 goal = ((u32 *)bh->b_data)[tmp];
  292.                 break;
  293.             }
  294.         }
  295.         if (!goal)
  296.             goal = bh->b_blocknr;
  297.     }
  298.     tmp = ext2_alloc_block (inode, goal);
  299.     if (!tmp) {
  300.         brelse (bh);
  301.         return NULL;
  302.     }
  303.     result = getblk (bh->b_dev, tmp, blocksize);
  304.     if (*p) {
  305.         ext2_free_blocks (inode->i_sb, tmp, 1);
  306.         brelse (result);
  307.         goto repeat;
  308.     }
  309.     *p = tmp;
  310.     mark_buffer_dirty(bh, 1);
  311.     if (IS_SYNC(inode) || inode->u.ext2_i.i_osync) {
  312.         ll_rw_block (WRITE, 1, &bh);
  313.         wait_on_buffer (bh);
  314.     }
  315.     inode->i_ctime = CURRENT_TIME;
  316.     inode->i_blocks += blocks;
  317.     inode->i_dirt = 1;
  318.     inode->u.ext2_i.i_next_alloc_block = new_block;
  319.     inode->u.ext2_i.i_next_alloc_goal = tmp;
  320.     brelse (bh);
  321.     return result;
  322. }
  323.  
  324. static int block_getcluster (struct inode * inode, struct buffer_head * bh,
  325.                       int nr,
  326.                       int blocksize)
  327. {
  328.     u32 * p;
  329.     int firstblock = 0;
  330.     int result = 0;
  331.     int i;
  332.  
  333.     /* Check to see if clustering possible here. */
  334.  
  335.     if(!bh) return 0;
  336.  
  337.     if(nr % (PAGE_SIZE / inode->i_sb->s_blocksize) != 0) goto out;
  338.     if(nr + 3 > EXT2_ADDR_PER_BLOCK(inode->i_sb)) goto out;
  339.  
  340.     for(i=0; i< (PAGE_SIZE / inode->i_sb->s_blocksize); i++) {
  341.       p = (u32 *) bh->b_data + nr + i;
  342.       
  343.       /* All blocks in cluster must already be allocated */
  344.       if(*p == 0) goto out;
  345.       
  346.       /* See if aligned correctly */
  347.       if(i==0) firstblock = *p;
  348.       else if(*p != firstblock + i) goto out;
  349.     }
  350.     
  351.     p = (u32 *) bh->b_data + nr;
  352.     result = generate_cluster(bh->b_dev, (int *) p, blocksize);
  353.  
  354.       out:
  355.     brelse(bh);
  356.     return result;
  357. }
  358.  
  359. struct buffer_head * ext2_getblk (struct inode * inode, long block,
  360.                   int create, int * err)
  361. {
  362.     struct buffer_head * bh;
  363.     unsigned long b;
  364.     unsigned long addr_per_block = EXT2_ADDR_PER_BLOCK(inode->i_sb);
  365.  
  366.     *err = -EIO;
  367.     if (block < 0) {
  368.         ext2_warning (inode->i_sb, "ext2_getblk", "block < 0");
  369.         return NULL;
  370.     }
  371.     if (block > EXT2_NDIR_BLOCKS + addr_per_block  +
  372.             addr_per_block * addr_per_block +
  373.             addr_per_block * addr_per_block * addr_per_block) {
  374.         ext2_warning (inode->i_sb, "ext2_getblk", "block > big");
  375.         return NULL;
  376.     }
  377.     /*
  378.      * If this is a sequential block allocation, set the next_alloc_block
  379.      * to this block now so that all the indblock and data block
  380.      * allocations use the same goal zone
  381.      */
  382.  
  383.     ext2_debug ("block %lu, next %lu, goal %lu.\n", block, 
  384.             inode->u.ext2_i.i_next_alloc_block,
  385.             inode->u.ext2_i.i_next_alloc_goal);
  386.  
  387.     if (block == inode->u.ext2_i.i_next_alloc_block + 1) {
  388.         inode->u.ext2_i.i_next_alloc_block++;
  389.         inode->u.ext2_i.i_next_alloc_goal++;
  390.     }
  391.  
  392.     *err = -ENOSPC;
  393.     b = block;
  394.     if (block < EXT2_NDIR_BLOCKS)
  395.         return inode_getblk (inode, block, create, b, err);
  396.     block -= EXT2_NDIR_BLOCKS;
  397.     if (block < addr_per_block) {
  398.         bh = inode_getblk (inode, EXT2_IND_BLOCK, create, b, err);
  399.         return block_getblk (inode, bh, block, create,
  400.                      inode->i_sb->s_blocksize, b, err);
  401.     }
  402.     block -= addr_per_block;
  403.     if (block < addr_per_block * addr_per_block) {
  404.         bh = inode_getblk (inode, EXT2_DIND_BLOCK, create, b, err);
  405.         bh = block_getblk (inode, bh, block / addr_per_block, create,
  406.                    inode->i_sb->s_blocksize, b, err);
  407.         return block_getblk (inode, bh, block & (addr_per_block - 1),
  408.                      create, inode->i_sb->s_blocksize, b, err);
  409.     }
  410.     block -= addr_per_block * addr_per_block;
  411.     bh = inode_getblk (inode, EXT2_TIND_BLOCK, create, b, err);
  412.     bh = block_getblk (inode, bh, block/(addr_per_block * addr_per_block),
  413.                create, inode->i_sb->s_blocksize, b, err);
  414.     bh = block_getblk (inode, bh, (block/addr_per_block) & (addr_per_block - 1),
  415.                create, inode->i_sb->s_blocksize, b, err);
  416.     return block_getblk (inode, bh, block & (addr_per_block - 1), create,
  417.                  inode->i_sb->s_blocksize, b, err);
  418. }
  419.  
  420. int ext2_getcluster (struct inode * inode, long block)
  421. {
  422.     struct buffer_head * bh;
  423.     int err, create;
  424.     unsigned long b;
  425.     unsigned long addr_per_block = EXT2_ADDR_PER_BLOCK(inode->i_sb);
  426.  
  427.     create = 0;
  428.     err = -EIO;
  429.     if (block < 0) {
  430.         ext2_warning (inode->i_sb, "ext2_getblk", "block < 0");
  431.         return 0;
  432.     }
  433.     if (block > EXT2_NDIR_BLOCKS + addr_per_block  +
  434.             addr_per_block * addr_per_block +
  435.             addr_per_block * addr_per_block * addr_per_block) {
  436.         ext2_warning (inode->i_sb, "ext2_getblk", "block > big");
  437.         return 0;
  438.     }
  439.  
  440.     err = -ENOSPC;
  441.     b = block;
  442.     if (block < EXT2_NDIR_BLOCKS) return 0;
  443.  
  444.     block -= EXT2_NDIR_BLOCKS;
  445.  
  446.     if (block < addr_per_block) {
  447.         bh = inode_getblk (inode, EXT2_IND_BLOCK, create, b, &err);
  448.         return block_getcluster (inode, bh, block, 
  449.                      inode->i_sb->s_blocksize);
  450.     }
  451.     block -= addr_per_block;
  452.     if (block < addr_per_block * addr_per_block) {
  453.         bh = inode_getblk (inode, EXT2_DIND_BLOCK, create, b, &err);
  454.         bh = block_getblk (inode, bh, block / addr_per_block, create,
  455.                    inode->i_sb->s_blocksize, b, &err);
  456.         return block_getcluster (inode, bh, block & (addr_per_block - 1),
  457.                      inode->i_sb->s_blocksize);
  458.     }
  459.     block -= addr_per_block * addr_per_block;
  460.     bh = inode_getblk (inode, EXT2_TIND_BLOCK, create, b, &err);
  461.     bh = block_getblk (inode, bh, block/(addr_per_block * addr_per_block),
  462.                create, inode->i_sb->s_blocksize, b, &err);
  463.     bh = block_getblk (inode, bh, (block/addr_per_block) & (addr_per_block - 1),
  464.                create, inode->i_sb->s_blocksize, b, &err);
  465.     return block_getcluster (inode, bh, block & (addr_per_block - 1),
  466.                  inode->i_sb->s_blocksize);
  467. }
  468.  
  469. struct buffer_head * ext2_bread (struct inode * inode, int block, 
  470.                  int create, int *err)
  471. {
  472.     struct buffer_head * bh;
  473.  
  474.     bh = ext2_getblk (inode, block, create, err);
  475.     if (!bh || bh->b_uptodate)
  476.         return bh;
  477.     ll_rw_block (READ, 1, &bh);
  478.     wait_on_buffer (bh);
  479.     if (bh->b_uptodate)
  480.         return bh;
  481.     brelse (bh);
  482.     *err = -EIO;
  483.     return NULL;
  484. }
  485.  
  486. void ext2_read_inode (struct inode * inode)
  487. {
  488.     struct buffer_head * bh;
  489.     struct ext2_inode * raw_inode;
  490.     unsigned long block_group;
  491.     unsigned long group_desc;
  492.     unsigned long desc;
  493.     unsigned long block;
  494.     struct ext2_group_desc * gdp;
  495.  
  496.     if ((inode->i_ino != EXT2_ROOT_INO && inode->i_ino != EXT2_ACL_IDX_INO &&
  497.          inode->i_ino != EXT2_ACL_DATA_INO && inode->i_ino < EXT2_FIRST_INO) ||
  498.         inode->i_ino > inode->i_sb->u.ext2_sb.s_es->s_inodes_count) {
  499.         ext2_error (inode->i_sb, "ext2_read_inode",
  500.                 "bad inode number: %lu", inode->i_ino);
  501.         return;
  502.     }
  503.     block_group = (inode->i_ino - 1) / EXT2_INODES_PER_GROUP(inode->i_sb);
  504.     if (block_group >= inode->i_sb->u.ext2_sb.s_groups_count)
  505.         ext2_panic (inode->i_sb, "ext2_read_inode",
  506.                 "group >= groups count");
  507.     group_desc = block_group / EXT2_DESC_PER_BLOCK(inode->i_sb);
  508.     desc = block_group % EXT2_DESC_PER_BLOCK(inode->i_sb);
  509.     bh = inode->i_sb->u.ext2_sb.s_group_desc[group_desc];
  510.     if (!bh)
  511.         ext2_panic (inode->i_sb, "ext2_read_inode",
  512.                 "Descriptor not loaded");
  513.     gdp = (struct ext2_group_desc *) bh->b_data;
  514.     block = gdp[desc].bg_inode_table +
  515.         (((inode->i_ino - 1) % EXT2_INODES_PER_GROUP(inode->i_sb))
  516.          / EXT2_INODES_PER_BLOCK(inode->i_sb));
  517.     if (!(bh = bread (inode->i_dev, block, inode->i_sb->s_blocksize)))
  518.         ext2_panic (inode->i_sb, "ext2_read_inode",
  519.                 "unable to read i-node block - "
  520.                 "inode=%lu, block=%lu", inode->i_ino, block);
  521.     raw_inode = ((struct ext2_inode *) bh->b_data) +
  522.         (inode->i_ino - 1) % EXT2_INODES_PER_BLOCK(inode->i_sb);
  523.     inode->i_mode = raw_inode->i_mode;
  524.     inode->i_uid = raw_inode->i_uid;
  525.     inode->i_gid = raw_inode->i_gid;
  526.     inode->i_nlink = raw_inode->i_links_count;
  527.     inode->i_size = raw_inode->i_size;
  528.     inode->i_atime = raw_inode->i_atime;
  529.     inode->i_ctime = raw_inode->i_ctime;
  530.     inode->i_mtime = raw_inode->i_mtime;
  531.     inode->u.ext2_i.i_dtime = raw_inode->i_dtime;
  532.     inode->i_blksize = inode->i_sb->s_blocksize;
  533.     inode->i_blocks = raw_inode->i_blocks;
  534.     inode->i_version = ++event;
  535.     inode->u.ext2_i.i_flags = raw_inode->i_flags;
  536.     inode->u.ext2_i.i_faddr = raw_inode->i_faddr;
  537.     inode->u.ext2_i.i_frag_no = raw_inode->i_frag;
  538.     inode->u.ext2_i.i_frag_size = raw_inode->i_fsize;
  539.     inode->u.ext2_i.i_osync = 0;
  540.     inode->u.ext2_i.i_file_acl = raw_inode->i_file_acl;
  541.     inode->u.ext2_i.i_dir_acl = raw_inode->i_dir_acl;
  542.     inode->u.ext2_i.i_version = raw_inode->i_version;
  543.     inode->u.ext2_i.i_block_group = block_group;
  544.     inode->u.ext2_i.i_next_alloc_block = 0;
  545.     inode->u.ext2_i.i_next_alloc_goal = 0;
  546.     if (inode->u.ext2_i.i_prealloc_count)
  547.         ext2_error (inode->i_sb, "ext2_read_inode",
  548.                 "New inode has non-zero prealloc count!");
  549.     if (S_ISCHR(inode->i_mode) || S_ISBLK(inode->i_mode))
  550.         inode->i_rdev = raw_inode->i_block[0];
  551.     else for (block = 0; block < EXT2_N_BLOCKS; block++)
  552.         inode->u.ext2_i.i_data[block] = raw_inode->i_block[block];
  553.     brelse (bh);
  554.     inode->i_op = NULL;
  555.     if (inode->i_ino == EXT2_ACL_IDX_INO ||
  556.         inode->i_ino == EXT2_ACL_DATA_INO)
  557.         /* Nothing to do */ ;
  558.     else if (S_ISREG(inode->i_mode))
  559.         inode->i_op = &ext2_file_inode_operations;
  560.     else if (S_ISDIR(inode->i_mode))
  561.         inode->i_op = &ext2_dir_inode_operations;
  562.     else if (S_ISLNK(inode->i_mode))
  563.         inode->i_op = &ext2_symlink_inode_operations;
  564.     else if (S_ISCHR(inode->i_mode))
  565.         inode->i_op = &chrdev_inode_operations;
  566.     else if (S_ISBLK(inode->i_mode))
  567.         inode->i_op = &blkdev_inode_operations;
  568.     else if (S_ISFIFO(inode->i_mode))
  569.         init_fifo(inode);
  570.     if (inode->u.ext2_i.i_flags & EXT2_SYNC_FL)
  571.         inode->i_flags |= MS_SYNCHRONOUS;
  572.     if (inode->u.ext2_i.i_flags & EXT2_APPEND_FL)
  573.         inode->i_flags |= S_APPEND;
  574.     if (inode->u.ext2_i.i_flags & EXT2_IMMUTABLE_FL)
  575.         inode->i_flags |= S_IMMUTABLE;
  576. }
  577.  
  578. static struct buffer_head * ext2_update_inode (struct inode * inode)
  579. {
  580.     struct buffer_head * bh;
  581.     struct ext2_inode * raw_inode;
  582.     unsigned long block_group;
  583.     unsigned long group_desc;
  584.     unsigned long desc;
  585.     unsigned long block;
  586.     struct ext2_group_desc * gdp;
  587.  
  588.     if ((inode->i_ino != EXT2_ROOT_INO && inode->i_ino < EXT2_FIRST_INO) ||
  589.         inode->i_ino > inode->i_sb->u.ext2_sb.s_es->s_inodes_count) {
  590.         ext2_error (inode->i_sb, "ext2_write_inode",
  591.                 "bad inode number: %lu", inode->i_ino);
  592.         return 0;
  593.     }
  594.     block_group = (inode->i_ino - 1) / EXT2_INODES_PER_GROUP(inode->i_sb);
  595.     if (block_group >= inode->i_sb->u.ext2_sb.s_groups_count)
  596.         ext2_panic (inode->i_sb, "ext2_write_inode",
  597.                 "group >= groups count");
  598.     group_desc = block_group / EXT2_DESC_PER_BLOCK(inode->i_sb);
  599.     desc = block_group % EXT2_DESC_PER_BLOCK(inode->i_sb);
  600.     bh = inode->i_sb->u.ext2_sb.s_group_desc[group_desc];
  601.     if (!bh)
  602.         ext2_panic (inode->i_sb, "ext2_write_inode",
  603.                 "Descriptor not loaded");
  604.     gdp = (struct ext2_group_desc *) bh->b_data;
  605.     block = gdp[desc].bg_inode_table +
  606.         (((inode->i_ino - 1) % EXT2_INODES_PER_GROUP(inode->i_sb))
  607.          / EXT2_INODES_PER_BLOCK(inode->i_sb));
  608.     if (!(bh = bread (inode->i_dev, block, inode->i_sb->s_blocksize)))
  609.         ext2_panic (inode->i_sb, "ext2_write_inode",
  610.                 "unable to read i-node block - "
  611.                 "inode=%lu, block=%lu", inode->i_ino, block);
  612.     raw_inode = ((struct ext2_inode *)bh->b_data) +
  613.         (inode->i_ino - 1) % EXT2_INODES_PER_BLOCK(inode->i_sb);
  614.     raw_inode->i_mode = inode->i_mode;
  615.     raw_inode->i_uid = inode->i_uid;
  616.     raw_inode->i_gid = inode->i_gid;
  617.     raw_inode->i_links_count = inode->i_nlink;
  618.     raw_inode->i_size = inode->i_size;
  619.     raw_inode->i_atime = inode->i_atime;
  620.     raw_inode->i_ctime = inode->i_ctime;
  621.     raw_inode->i_mtime = inode->i_mtime;
  622.     raw_inode->i_blocks = inode->i_blocks;
  623.     raw_inode->i_dtime = inode->u.ext2_i.i_dtime;
  624.     raw_inode->i_flags = inode->u.ext2_i.i_flags;
  625.     raw_inode->i_faddr = inode->u.ext2_i.i_faddr;
  626.     raw_inode->i_frag = inode->u.ext2_i.i_frag_no;
  627.     raw_inode->i_fsize = inode->u.ext2_i.i_frag_size;
  628.     raw_inode->i_file_acl = inode->u.ext2_i.i_file_acl;
  629.     raw_inode->i_dir_acl = inode->u.ext2_i.i_dir_acl;
  630.     raw_inode->i_version = inode->u.ext2_i.i_version;
  631.     if (S_ISCHR(inode->i_mode) || S_ISBLK(inode->i_mode))
  632.         raw_inode->i_block[0] = inode->i_rdev;
  633.     else for (block = 0; block < EXT2_N_BLOCKS; block++)
  634.         raw_inode->i_block[block] = inode->u.ext2_i.i_data[block];
  635.     mark_buffer_dirty(bh, 1);
  636.     inode->i_dirt = 0;
  637.     return bh;
  638. }
  639.  
  640. void ext2_write_inode (struct inode * inode)
  641. {
  642.     struct buffer_head * bh;
  643.     bh = ext2_update_inode (inode);
  644.     brelse (bh);
  645. }
  646.  
  647. int ext2_sync_inode (struct inode *inode)
  648. {
  649.     int err = 0;
  650.     struct buffer_head *bh;
  651.  
  652.     bh = ext2_update_inode (inode);
  653.     if (bh && bh->b_dirt)
  654.     {
  655.         ll_rw_block (WRITE, 1, &bh);
  656.         wait_on_buffer (bh);
  657.         if (bh->b_req && !bh->b_uptodate)
  658.         {
  659.             printk ("IO error syncing ext2 inode [%04x:%08lx]\n",
  660.                 inode->i_dev, inode->i_ino);
  661.             err = -1;
  662.         }
  663.     }
  664.     else if (!bh)
  665.         err = -1;
  666.     brelse (bh);
  667.     return err;
  668. }
  669.