1. 15 2月, 2011 1 次提交
  2. 06 2月, 2011 1 次提交
    • J
      Btrfs: exclude super blocks when we read in block groups · 3c14874a
      Josef Bacik 提交于
      This has been resulting in a BUT_ON(ret) after btrfs_reserve_extent in
      btrfs_cow_file_range.  The reason is we don't actually calculate the bytes_super
      for a block group until we go to cache it, which means that the space_info can
      hand out reservations for space that it doesn't actually have, and we can run
      out of data space.  This is also a problem if you are using space caching since
      we don't ever calculate bytes_super for the block groups.  So instead everytime
      we read a block group call exclude_super_stripes, which calculates the
      bytes_super for the block group so it can be left out of the space_info.  Then
      whenever caching completes we just call free_excluded_extents so that the super
      excluded extents are freed up.  Also if we are unmounting and we hit any block
      groups that haven't been cached we still need to call free_excluded_extents to
      make sure things are cleaned up properly.  Thanks,
      Reported-by: NArne Jansen <sensille@gmx.net>
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      Signed-off-by: NChris Mason <chris.mason@oracle.com>
      3c14874a
  3. 01 2月, 2011 3 次提交
  4. 29 1月, 2011 3 次提交
    • J
      Btrfs: use the global block reserve if we cannot reserve space · 68a82277
      Josef Bacik 提交于
      We call use_block_rsv right before we make an allocation in order to make sure
      we have enough space.  Now normally people have called btrfs_start_transaction()
      with the appropriate amount of space that we need, so we just use some of that
      pre-reserved space and move along happily.  The problem is where people use
      btrfs_join_transaction(), which doesn't actually reserve any space.  So we try
      and reserve space here, but we cannot flush delalloc, so this forces us to
      return -ENOSPC when in reality we have plenty of space.  The most common symptom
      is seeing a bunch of "couldn't dirty inode" messages in syslog.  With
      xfstests 224 we end up falling back to start_transaction and then doing all the
      flush delalloc stuff which causes to hang for a very long time.
      
      So instead steal from the global reserve, which is what this is meant for
      anyway.  With this patch and the other 2 I have sent xfstests 224 now passes
      successfully.  Thanks,
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      Signed-off-by: NChris Mason <chris.mason@oracle.com>
      68a82277
    • J
      Btrfs: do not release more reserved bytes to the global_block_rsv than we need · e9e22899
      Josef Bacik 提交于
      When we do btrfs_block_rsv_release, if global_block_rsv is not full we will
      release all the extra bytes to global_block_rsv, even if it's only a little
      short of the amount of space that we need to reserve.  This causes us to starve
      ourselves of reservable space during the transaction which will force us to
      shrink delalloc bytes and commit the transaction more often than we should.  So
      instead just add the amount of bytes we need to add to the global reserve so
      reserved == size, and then add the rest back into the space_info for general
      use.  Thanks,
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      Signed-off-by: NChris Mason <chris.mason@oracle.com>
      e9e22899
    • T
      btrfs: fix return value check of btrfs_join_transaction() · 3612b495
      Tsutomu Itoh 提交于
      The error check of btrfs_join_transaction()/btrfs_join_transaction_nolock()
      is added, and the mistake of the error check in several places is
      corrected.
      
      For more stable Btrfs, I think that we should reduce BUG_ON().
      But, I think that long time is necessary for this.
      So, I propose this patch as a short-term solution.
      
      With this patch:
       - To more stable Btrfs, the part that should be corrected is clarified.
       - The panic isn't done by the NULL pointer reference etc. (even if
         BUG_ON() is increased temporarily)
       - The error code is returned in the place where the error can be easily
         returned.
      
      As a long-term plan:
       - BUG_ON() is reduced by using the forced-readonly framework, etc.
      Signed-off-by: NTsutomu Itoh <t-itoh@jp.fujitsu.com>
      Signed-off-by: NChris Mason <chris.mason@oracle.com>
      3612b495
  5. 18 1月, 2011 1 次提交
    • L
      Btrfs: forced readonly mounts on errors · acce952b
      liubo 提交于
      This patch comes from "Forced readonly mounts on errors" ideas.
      
      As we know, this is the first step in being more fault tolerant of disk
      corruptions instead of just using BUG() statements.
      
      The major content:
      - add a framework for generating errors that should result in filesystems
        going readonly.
      - keep FS state in disk super block.
      - make sure that all of resource will be freed and released at umount time.
      - make sure that fter FS is forced readonly on error, there will be no more
        disk change before FS is corrected. For this, we should stop write operation.
      
      After this patch is applied, the conversion from BUG() to such a framework can
      happen incrementally.
      Signed-off-by: NLiu Bo <liubo2009@cn.fujitsu.com>
      Signed-off-by: NChris Mason <chris.mason@oracle.com>
      acce952b
  6. 17 1月, 2011 4 次提交
    • J
      Btrfs: don't warn if we get ENOSPC in btrfs_block_rsv_check · f690efb1
      Josef Bacik 提交于
      If we run low on space we could get a bunch of warnings out of
      btrfs_block_rsv_check, but this is mostly just called via the transaction code
      to see if we need to end the transaction, it expects to see failures, so let's
      not WARN and freak everybody out for no reason.  Thanks,
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      Signed-off-by: NChris Mason <chris.mason@oracle.com>
      f690efb1
    • M
      btrfs: fix wrong free space information of btrfs · 6d07bcec
      Miao Xie 提交于
      When we store data by raid profile in btrfs with two or more different size
      disks, df command shows there is some free space in the filesystem, but the
      user can not write any data in fact, df command shows the wrong free space
      information of btrfs.
      
       # mkfs.btrfs -d raid1 /dev/sda9 /dev/sda10
       # btrfs-show
       Label: none  uuid: a95cd49e-6e33-45b8-8741-a36153ce4b64
       	Total devices 2 FS bytes used 28.00KB
       	devid    1 size 5.01GB used 2.03GB path /dev/sda9
       	devid    2 size 10.00GB used 2.01GB path /dev/sda10
       # btrfs device scan /dev/sda9 /dev/sda10
       # mount /dev/sda9 /mnt
       # dd if=/dev/zero of=tmpfile0 bs=4K count=9999999999
         (fill the filesystem)
       # sync
       # df -TH
       Filesystem	Type	Size	Used	Avail	Use%	Mounted on
       /dev/sda9	btrfs	17G	8.6G	5.4G	62%	/mnt
       # btrfs-show
       Label: none  uuid: a95cd49e-6e33-45b8-8741-a36153ce4b64
       	Total devices 2 FS bytes used 3.99GB
       	devid    1 size 5.01GB used 5.01GB path /dev/sda9
       	devid    2 size 10.00GB used 4.99GB path /dev/sda10
      
      It is because btrfs cannot allocate chunks when one of the pairing disks has
      no space, the free space on the other disks can not be used for ever, and should
      be subtracted from the total space, but btrfs doesn't subtract this space from
      the total. It is strange to the user.
      
      This patch fixes it by calcing the free space that can be used to allocate
      chunks.
      
      Implementation:
      1. get all the devices free space, and align them by stripe length.
      2. sort the devices by the free space.
      3. check the free space of the devices,
         3.1. if it is not zero, and then check the number of the devices that has
              more free space than this device,
              if the number of the devices is beyond the min stripe number, the free
              space can be used, and add into total free space.
              if the number of the devices is below the min stripe number, we can not
              use the free space, the check ends.
         3.2. if the free space is zero, check the next devices, goto 3.1
      
      This implementation is just likely fake chunk allocation.
      
      After appling this patch, df can show correct space information:
       # df -TH
       Filesystem	Type	Size	Used	Avail	Use%	Mounted on
       /dev/sda9	btrfs	17G	8.6G	0	100%	/mnt
      Signed-off-by: NMiao Xie <miaox@cn.fujitsu.com>
      Signed-off-by: NChris Mason <chris.mason@oracle.com>
      6d07bcec
    • M
      btrfs: restructure find_free_dev_extent() · 7bfc837d
      Miao Xie 提交于
      - make it return the start position and length of the max free space when it can
        not find a suitable free space.
      - make it more readability
      Signed-off-by: NMiao Xie <miaox@cn.fujitsu.com>
      Signed-off-by: NChris Mason <chris.mason@oracle.com>
      7bfc837d
    • M
      btrfs: try to reclaim some space when chunk allocation fails · d52a5b5f
      Miao Xie 提交于
      We cannot write data into files when when there is tiny space in the filesystem.
      
      Reproduce steps:
       # mkfs.btrfs /dev/sda1
       # mount /dev/sda1 /mnt
       # dd if=/dev/zero of=/mnt/tmpfile0 bs=4K count=1
       # dd if=/dev/zero of=/mnt/tmpfile1 bs=4K count=99999999999999
         (fill the filesystem)
       # umount /mnt
       # mount /dev/sda1 /mnt
       # rm -f /mnt/tmpfile0
       # dd if=/dev/zero of=/mnt/tmpfile0 bs=4K count=1
         (failed with nospec)
      
      But if we do the last step again, we can write data successfully. The reason of
      the problem is that btrfs didn't try to commit the current transaction and
      reclaim some space when chunk allocation failed.
      
      This patch fixes it by committing the current transaction to reclaim some
      space when chunk allocation fails.
      Signed-off-by: NMiao Xie <miaox@cn.fujitsu.com>
      Reviewed-by: NJosef Bacik <josef@redhat.com>
      Signed-off-by: NChris Mason <chris.mason@oracle.com>
      d52a5b5f
  7. 05 1月, 2011 1 次提交
  8. 14 12月, 2010 2 次提交
    • C
      Btrfs: prevent RAID level downgrades when space is low · 83a50de9
      Chris Mason 提交于
      The extent allocator has code that allows us to fill
      allocations from any available block group, even if it doesn't
      match the raid level we've requested.
      
      This was put in because adding a new drive to a filesystem
      made with the default mkfs options actually upgrades the metadata from
      single spindle dup to full RAID1.
      
      But, the code also allows us to allocate from a raid0 chunk when we
      really want a raid1 or raid10 chunk.  This can cause big trouble because
      mkfs creates a small (4MB) raid0 chunk for data and metadata which then
      goes unused for raid1/raid10 installs.
      
      The allocator will happily wander in and allocate from that chunk when
      things get tight, which is not correct.
      
      The fix here is to make sure that we provide duplication when the
      caller has asked for it.  It does all the dups to be any raid level,
      which preserves the dup->raid1 upgrade abilities.
      Signed-off-by: NChris Mason <chris.mason@oracle.com>
      83a50de9
    • C
      Btrfs: account for missing devices in RAID allocation profiles · cd02dca5
      Chris Mason 提交于
      When we mount in RAID degraded mode without adding a new device to
      replace the failed one, we can end up using the wrong RAID flags for
      allocations.
      
      This results in strange combinations of block groups (raid1 in a raid10
      filesystem) and corruptions when we try to allocate blocks from single
      spindle chunks on drives that are actually missing.
      
      The first device has two small 4MB chunks in it that mkfs creates and
      these are usually unused in a raid1 or raid10 setup.  But, in -o degraded,
      the allocator will fall back to these because the mask of desired raid groups
      isn't correct.
      
      The fix here is to count the missing devices as we build up the list
      of devices in the system.  This count is used when picking the
      raid level to make sure we continue using the same levels that were
      in place before we lost a drive.
      Signed-off-by: NChris Mason <chris.mason@oracle.com>
      cd02dca5
  9. 11 12月, 2010 1 次提交
  10. 10 12月, 2010 2 次提交
    • J
      Btrfs: do not do fast caching if we are allocating blocks for tree_root · b8399dee
      Josef Bacik 提交于
      Since the fast caching uses normal tree locking, we can possibly deadlock if we
      get to the caching via a btrfs_search_slot() on the tree_root.  So just check to
      see if the root we are on is the tree root, and just don't do the fast caching.
      Reported-by: NSage Weil <sage@newdream.net>
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      b8399dee
    • J
      Btrfs: deal with space cache errors better · 2b20982e
      Josef Bacik 提交于
      Currently if the space cache inode generation number doesn't match the
      generation number in the space cache header we will just fail to load the space
      cache, but we won't mark the space cache as an error, so we'll keep getting that
      error each time somebody tries to cache that block group until we actually clear
      the thing.  Fix this by marking the space cache as having an error so we only
      get the message once.  This patch also makes it so that we don't try and setup
      space cache for a block group that isn't cached, since we won't be able to write
      it out anyway.  None of these problems are actual problems, they are just
      annoying and sub-optimal.  Thanks,
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      2b20982e
  11. 22 11月, 2010 1 次提交
  12. 30 10月, 2010 2 次提交
  13. 29 10月, 2010 9 次提交
    • C
      Btrfs: use the flusher threads for delalloc throttling · bf9022e0
      Chris Mason 提交于
      We have a fairly complex set of loops around walking our list of
      delalloc inodes when we find metadata delalloc space running low.
      It doesn't work very well, can use large amounts of CPU and doesn't
      do very efficient writeback.
      
      This switches us to kick the bdi flusher threads instead.  All dirty
      data in btrfs is accounted as delalloc data, so this is very similar
      in terms of what it writes, but we're able to just kick off the IO
      and wait for progress.
      Signed-off-by: NChris Mason <chris.mason@oracle.com>
      bf9022e0
    • C
      Btrfs: tune the chunk allocation to 5% of the FS as metadata · e5bc2458
      Chris Mason 提交于
      An earlier commit tried to keep us from allocating too many
      empty metadata chunks.  It was somewhat too restrictive and could
      lead to ENOSPC errors on empty filesystems.
      
      This increases the limits to about 5% of the FS size, allowing more
      metadata chunks to be preallocated.
      Signed-off-by: NChris Mason <chris.mason@oracle.com>
      e5bc2458
    • J
      Btrfs: let the user know space caching is enabled · 8216ef86
      Josef Bacik 提交于
      If you mount -o space_cache, the option will be persistent across mounts, but to
      make sure the user knows that they did this, emit a message telling them if they
      didn't mount with -o space_cache but the feature is still used.
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      8216ef86
    • J
      Btrfs: Add a clear_cache mount option · 88c2ba3b
      Josef Bacik 提交于
      If something goes wrong with the free space cache we need a way to make sure
      it's not loaded on mount and that it's cleared for everybody.  When you pass the
      clear_cache option it will make it so all block groups are setup to be cleared,
      which keeps them from being loaded and then they will be truncated when the
      transaction is committed.  Thanks,
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      88c2ba3b
    • J
      Btrfs: add support for mixed data+metadata block groups · 67377734
      Josef Bacik 提交于
      There are just a few things that need to be fixed in the kernel to support mixed
      data+metadata block groups.  Mostly we just need to make sure that if we are
      using mixed block groups that we continue to allocate mixed block groups as we
      need them.  Also we need to make sure __find_space_info will find our space info
      if we search for DATA or METADATA only.  Tested this with xfstests and it works
      nicely.  Thanks,
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      67377734
    • J
      Btrfs: check cache->caching_ctl before returning if caching has started · dde5abee
      Josef Bacik 提交于
      With the free space disk caching we can mark the block group as started with the
      caching, but we don't have a caching ctl.  This can race with anybody else who
      tries to get the caching ctl before we cache (this is very hard to do btw).  So
      instead check to see if cache->caching_ctl is set, and if not return NULL.
      Thanks,
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      dde5abee
    • J
      Btrfs: load free space cache if it exists · 9d66e233
      Josef Bacik 提交于
      This patch actually loads the free space cache if it exists.  The only thing
      that really changes here is that we need to cache the block group if we're going
      to remove an extent from it.  Previously we did not do this since the caching
      kthread would pick it up.  With the on disk cache we don't have this luxury so
      we need to make sure we read the on disk cache in first, and then remove the
      extent, that way when the extent is unpinned the free space is added to the
      block group.  This has been tested with all sorts of things.
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      9d66e233
    • J
      Btrfs: write out free space cache · 0cb59c99
      Josef Bacik 提交于
      This is a simple bit, just dump the free space cache out to our preallocated
      inode when we're writing out dirty block groups.  There are a bunch of changes
      in inode.c in order to account for special cases.  Mostly when we're doing the
      writeout we're holding trans_mutex, so we need to use the nolock transacation
      functions.  Also we can't do asynchronous completions since the async thread
      could be blocked on already completed IO waiting for the transaction lock.  This
      has been tested with xfstests and btrfs filesystem balance, as well as my ENOSPC
      tests.  Thanks,
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      0cb59c99
    • J
      Btrfs: create special free space cache inode · 0af3d00b
      Josef Bacik 提交于
      In order to save free space cache, we need an inode to hold the data, and we
      need a special item to point at the right inode for the right block group.  So
      first, create a special item that will point to the right inode, and the number
      of extent entries we will have and the number of bitmaps we will have.  We
      truncate and pre-allocate space everytime to make sure it's uptodate.
      
      This feature will be turned on as soon as you mount with -o space_cache, however
      it is safe to boot into old kernels, they will just generate the cache the old
      fashion way.  When you boot back into a newer kernel we will notice that we
      modified and not the cache and automatically discard the cache.
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      0af3d00b
  14. 27 10月, 2010 2 次提交
    • J
      Btrfs: remove warn_on from use_block_rsv · e9bb7f10
      Josef Bacik 提交于
      Because btrfs_dirty_inode does a btrfs_join_transaction, it doesn't actually
      reserve space.  It does this so we can try and dirty the inode quickly without
      having to deal with the ENOSPC problems.  But if it does get back ENOSPC it
      handles it properly.  The problem is use_block_rsv does a WARN_ON whenever this
      case happens, even tho btrfs_dirty_inode takes it into account and actually
      expects to get -ENOSPC if things are particularly tight.  So instead just remove
      the warning.  Thanks,
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      e9bb7f10
    • J
      Btrfs: set trans to null in reserve_metadata_bytes if we commit the transaction · 38227933
      Josef Bacik 提交于
      btrfs_commit_transaction will free our trans, but because we pass trans to
      shrink_delalloc we could possibly have a use after free situation.  So instead
      if we commit the transaction, set trans to null and set committed to true so we
      don't keep trying to commit a transaction.  This fixes a panic I could reproduce
      at will.  Thanks,
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      38227933
  15. 23 10月, 2010 6 次提交
    • J
      Btrfs: rework how we reserve metadata bytes · 8bb8ab2e
      Josef Bacik 提交于
      With multi-threaded writes we were getting ENOSPC early because somebody would
      come in, start flushing delalloc because they couldn't make their reservation,
      and in the meantime other threads would come in and use the space that was
      getting freed up, so when the original thread went to check to see if they had
      space they didn't and they'd return ENOSPC.  So instead if we have some free
      space but not enough for our reservation, take the reservation and then start
      doing the flushing.  The only time we don't take reservations is when we've
      already overcommitted our space, that way we don't have people who come late to
      the party way overcommitting ourselves.  This also moves all of the retrying and
      flushing code into reserve_metdata_bytes so it's all uniform.  This keeps my
      fs_mark test from returning -ENOSPC as soon as it starts and actually lets me
      fill up the disk.  Thanks,
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      8bb8ab2e
    • J
      Btrfs: don't allocate chunks as aggressively · 14ed0ca6
      Josef Bacik 提交于
      Because the ENOSPC code over reserves super aggressively we end up allocating
      chunks way more often than we should.  For example with my fs_mark tests on a
      2gb fs I can end up reserved 1gb just for metadata, when only 34mb of that is
      being used.  So instead check to see if the amount of space actually used is
      less than 30% of the total space, and if so don't allocate a chunk, but only if
      we have at least 256mb of free space to make sure we don't put too much pressure
      on free space.
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      14ed0ca6
    • J
      Btrfs: re-work delalloc flushing · 0019f10d
      Josef Bacik 提交于
      Currently we try and flush delalloc, but we only do that in a sort of weak way,
      which works fine in most cases but if we're under heavy pressure we need to be
      able to wait for flushing to happen.  Also instead of checking the bytes
      reserved in the block_rsv, check the space info since it is more accurate.  The
      sync option will be used in a future patch.
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      0019f10d
    • J
      Btrfs: fix reservation code for mixed block groups · 6d48755d
      Josef Bacik 提交于
      The global reservation stuff tries to add together DATA and METADATA used in
      order to figure out how much to reserve for everything, but this doesn't work
      right for mixed block groups.  Instead if we have mixed block groups just set
      data used to 0.  Also with mixed block groups we will use bytes_may_use for
      keeping track of delalloc bytes, so we need to take that into account in our
      reservation calculations.
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      6d48755d
    • J
      Btrfs: fix df regression · 89a55897
      Josef Bacik 提交于
      The new ENOSPC stuff breaks out the raid types which breaks the way we were
      reporting df to the system.  This fixes it back so that Available is the total
      space available to data and used is the actual bytes used by the filesystem.
      This means that Available is Total - data used - all of the metadata space.
      Thanks,
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      89a55897
    • J
      Btrfs: stop trying to shrink delalloc if there are no inodes to reclaim · a1f76506
      Josef Bacik 提交于
      In very severe ENOSPC cases we can run out of inodes to do delalloc on, which
      means we'll just keep looping trying to shrink delalloc.  Instead, if we fail to
      shrink delalloc 3 times in a row break out since we're not likely to make any
      progress.  Tested this with a 100mb fs an xfstests test 13.  Before the patch it
      would hang the box, with the patch we get -ENOSPC like we should.  Thanks,
      Signed-off-by: NJosef Bacik <josef@redhat.com>
      a1f76506
  16. 17 9月, 2010 1 次提交
    • C
      block: remove BLKDEV_IFL_WAIT · dd3932ed
      Christoph Hellwig 提交于
      All the blkdev_issue_* helpers can only sanely be used for synchronous
      caller.  To issue cache flushes or barriers asynchronously the caller needs
      to set up a bio by itself with a completion callback to move the asynchronous
      state machine ahead.  So drop the BLKDEV_IFL_WAIT flag that is always
      specified when calling blkdev_issue_* and also remove the now unused flags
      argument to blkdev_issue_flush and blkdev_issue_zeroout.  For
      blkdev_issue_discard we need to keep it for the secure discard flag, which
      gains a more descriptive name and loses the bitops vs flag confusion.
      Signed-off-by: NChristoph Hellwig <hch@lst.de>
      Signed-off-by: NJens Axboe <jaxboe@fusionio.com>
      dd3932ed