]> git.apps.os.sepia.ceph.com Git - ceph.git/commitdiff
zone block offset bug fix and related unit test case
authorRamesh Chander <Ramesh.Chander@sandisk.com>
Sun, 18 Dec 2016 18:23:42 +0000 (10:23 -0800)
committerRamesh Chander <Ramesh.Chander@sandisk.com>
Sun, 18 Dec 2016 18:40:40 +0000 (10:40 -0800)
Signed-off-by: Ramesh Chander <Ramesh.Chander@sandisk.com>
zone block offset related test case

Signed-off-by: Ramesh Chander <Ramesh.Chander@sandisk.com>
src/os/bluestore/BitAllocator.cc
src/test/objectstore/BitAllocator_test.cc

index 2dfe190275a6820cbe486e08a5034cfb29d7488c..d2ed8102747258b4e3694bd30b62e1003bc9ec35 100644 (file)
@@ -195,6 +195,7 @@ void BmapEntry::clear_bits(int offset, int num_bits)
   if (num_bits == 0) {
     return;
   }
+
   bmap_t bmask = BmapEntry::align_mask(num_bits) >> offset;
   m_bits &= ~(bmask);
 }
@@ -504,17 +505,25 @@ void BitMapZone::free_blocks_int(int64_t start_block, int64_t num_blocks)
   BmapEntry *bmap = NULL;
   int bit = 0;
   int64_t falling_in_bmap = 0;
+  int64_t count = num_blocks;
+  int64_t first_blk = start_block;
+  
+  if (num_blocks == 0) {
+    return; 
+  }
+  alloc_dbg_assert(is_allocated(start_block, num_blocks));
 
-  while (num_blocks) {
-    bit = start_block % BmapEntry::size();
-    bmap = &(*m_bmap_list)[start_block / BmapEntry::size()];
-    falling_in_bmap = MIN(num_blocks, BmapEntry::size() - bit);
+  while (count) {
+    bit = first_blk % BmapEntry::size();
+    bmap = &(*m_bmap_list)[first_blk / BmapEntry::size()];
+    falling_in_bmap = MIN(count, BmapEntry::size() - bit);
 
     bmap->clear_bits(bit, falling_in_bmap);
 
-    start_block += falling_in_bmap;
-    num_blocks -= falling_in_bmap;
+    first_blk += falling_in_bmap;
+    count -= falling_in_bmap;
   }
+  alloc_dbg_assert(!is_allocated(start_block, num_blocks));
 }
 
 void BitMapZone::lock_excl()
@@ -581,7 +590,9 @@ int64_t BitMapZone::alloc_blocks_dis(int64_t num_blocks,
       last_cont += alloc_cont;
       
       if (!alloc_cont) {
-        this->free_blocks_int(last_running_ext, last_cont);
+        if (last_cont) {
+          this->free_blocks_int(last_running_ext - zone_blk_off, last_cont);
+        }
         allocated -= last_cont;
         last_cont = 0;
       } else if (last_cont / min_alloc) {
@@ -624,7 +635,9 @@ int64_t BitMapZone::alloc_blocks_dis(int64_t num_blocks,
       search_idx = 0;
       bmap_idx = iter.index();
       if ((bmap = iter.next()) == NULL) {
-        this->free_blocks_int(last_running_ext, last_cont);
+        if (last_cont) {
+          this->free_blocks_int(last_running_ext - zone_blk_off, last_cont);
+        }
         allocated -= last_cont;
         break;
       }
index d5ca99d6e8df56e58ede1018426a1aef3d4d0d30..09460a153b6f0987c5b2ba8b621b2e6af4345f25 100644 (file)
@@ -335,14 +335,52 @@ TEST(BitAllocator, test_zone_alloc)
         delete zone;
       }
     }
+
+    //allocation in loop
+    {
+      ExtentList *block_list = new ExtentList(&extents, blk_size);
+      zone = new BitMapZone(total_blocks, 0);
+      lock = zone->lock_excl_try();
+
+      for (int iter = 1; iter < 5; iter++) {
+        for (int i = 1; i <= total_blocks; i = i << 1) {
+          for (int j = 0; j < total_blocks; j +=i) {
+            bmap_test_assert(lock);
+            block_list->reset();
+            int64_t need_blks = i;
+            allocated = zone->alloc_blocks_dis(need_blks, i, 0, 0, block_list);
+            bmap_test_assert(allocated == need_blks);
+            bmap_test_assert(extents[0].offset ==  (uint64_t) j);
+            block_list->reset();
+          }
+          {
+            allocated = zone->alloc_blocks_dis(1, 1, 0, 0, block_list);
+            bmap_test_assert(allocated == 0);
+            block_list->reset();
+          }
+         
+          for (int j = 0; j < total_blocks; j +=i) {
+            zone->free_blocks(j, i);
+          }
+        }
+      }
+      delete block_list;
+      delete zone;
+    }
+
     {
+
         ExtentList *block_list = new ExtentList(&extents, blk_size);
         zone = new BitMapZone(total_blocks, 0);
         lock = zone->lock_excl_try();
         bmap_test_assert(lock);
 
         block_list->reset();
-        allocated = zone->alloc_blocks_dis(total_blocks + 1, total_blocks + 1, 0, 0, block_list);
+        allocated = zone->alloc_blocks_dis(total_blocks + 1, total_blocks + 1, 0, 1024, block_list);
+        bmap_test_assert(allocated == 0);  
+
+        block_list->reset();
+        allocated = zone->alloc_blocks_dis(total_blocks, total_blocks, 1, 1024, block_list);
         bmap_test_assert(allocated == 0);  
 
         block_list->reset();