1 /* 2 * Block Dirty Bitmap 3 * 4 * Copyright (c) 2016-2017 Red Hat. Inc 5 * 6 * Permission is hereby granted, free of charge, to any person obtaining a copy 7 * of this software and associated documentation files (the "Software"), to deal 8 * in the Software without restriction, including without limitation the rights 9 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 * copies of the Software, and to permit persons to whom the Software is 11 * furnished to do so, subject to the following conditions: 12 * 13 * The above copyright notice and this permission notice shall be included in 14 * all copies or substantial portions of the Software. 15 * 16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 19 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 * THE SOFTWARE. 23 */ 24 #include "qemu/osdep.h" 25 #include "qapi/error.h" 26 #include "qemu-common.h" 27 #include "trace.h" 28 #include "block/block_int.h" 29 #include "block/blockjob.h" 30 31 /** 32 * A BdrvDirtyBitmap can be in three possible states: 33 * (1) successor is NULL and disabled is false: full r/w mode 34 * (2) successor is NULL and disabled is true: read only mode ("disabled") 35 * (3) successor is set: frozen mode. 36 * A frozen bitmap cannot be renamed, deleted, anonymized, cleared, set, 37 * or enabled. A frozen bitmap can only abdicate() or reclaim(). 38 */ 39 struct BdrvDirtyBitmap { 40 QemuMutex *mutex; 41 HBitmap *bitmap; /* Dirty bitmap implementation */ 42 HBitmap *meta; /* Meta dirty bitmap */ 43 BdrvDirtyBitmap *successor; /* Anonymous child; implies frozen status */ 44 char *name; /* Optional non-empty unique ID */ 45 int64_t size; /* Size of the bitmap, in bytes */ 46 bool disabled; /* Bitmap is disabled. It ignores all writes to 47 the device */ 48 int active_iterators; /* How many iterators are active */ 49 bool readonly; /* Bitmap is read-only. This field also 50 prevents the respective image from being 51 modified (i.e. blocks writes and discards). 52 Such operations must fail and both the image 53 and this bitmap must remain unchanged while 54 this flag is set. */ 55 bool autoload; /* For persistent bitmaps: bitmap must be 56 autoloaded on image opening */ 57 bool persistent; /* bitmap must be saved to owner disk image */ 58 QLIST_ENTRY(BdrvDirtyBitmap) list; 59 }; 60 61 struct BdrvDirtyBitmapIter { 62 HBitmapIter hbi; 63 BdrvDirtyBitmap *bitmap; 64 }; 65 66 static inline void bdrv_dirty_bitmaps_lock(BlockDriverState *bs) 67 { 68 qemu_mutex_lock(&bs->dirty_bitmap_mutex); 69 } 70 71 static inline void bdrv_dirty_bitmaps_unlock(BlockDriverState *bs) 72 { 73 qemu_mutex_unlock(&bs->dirty_bitmap_mutex); 74 } 75 76 void bdrv_dirty_bitmap_lock(BdrvDirtyBitmap *bitmap) 77 { 78 qemu_mutex_lock(bitmap->mutex); 79 } 80 81 void bdrv_dirty_bitmap_unlock(BdrvDirtyBitmap *bitmap) 82 { 83 qemu_mutex_unlock(bitmap->mutex); 84 } 85 86 /* Called with BQL or dirty_bitmap lock taken. */ 87 BdrvDirtyBitmap *bdrv_find_dirty_bitmap(BlockDriverState *bs, const char *name) 88 { 89 BdrvDirtyBitmap *bm; 90 91 assert(name); 92 QLIST_FOREACH(bm, &bs->dirty_bitmaps, list) { 93 if (bm->name && !strcmp(name, bm->name)) { 94 return bm; 95 } 96 } 97 return NULL; 98 } 99 100 /* Called with BQL taken. */ 101 void bdrv_dirty_bitmap_make_anon(BdrvDirtyBitmap *bitmap) 102 { 103 assert(!bdrv_dirty_bitmap_frozen(bitmap)); 104 g_free(bitmap->name); 105 bitmap->name = NULL; 106 bitmap->persistent = false; 107 bitmap->autoload = false; 108 } 109 110 /* Called with BQL taken. */ 111 BdrvDirtyBitmap *bdrv_create_dirty_bitmap(BlockDriverState *bs, 112 uint32_t granularity, 113 const char *name, 114 Error **errp) 115 { 116 int64_t bitmap_size; 117 BdrvDirtyBitmap *bitmap; 118 119 assert(is_power_of_2(granularity) && granularity >= BDRV_SECTOR_SIZE); 120 121 if (name && bdrv_find_dirty_bitmap(bs, name)) { 122 error_setg(errp, "Bitmap already exists: %s", name); 123 return NULL; 124 } 125 bitmap_size = bdrv_getlength(bs); 126 if (bitmap_size < 0) { 127 error_setg_errno(errp, -bitmap_size, "could not get length of device"); 128 errno = -bitmap_size; 129 return NULL; 130 } 131 bitmap = g_new0(BdrvDirtyBitmap, 1); 132 bitmap->mutex = &bs->dirty_bitmap_mutex; 133 bitmap->bitmap = hbitmap_alloc(bitmap_size, ctz32(granularity)); 134 bitmap->size = bitmap_size; 135 bitmap->name = g_strdup(name); 136 bitmap->disabled = false; 137 bdrv_dirty_bitmaps_lock(bs); 138 QLIST_INSERT_HEAD(&bs->dirty_bitmaps, bitmap, list); 139 bdrv_dirty_bitmaps_unlock(bs); 140 return bitmap; 141 } 142 143 /* bdrv_create_meta_dirty_bitmap 144 * 145 * Create a meta dirty bitmap that tracks the changes of bits in @bitmap. I.e. 146 * when a dirty status bit in @bitmap is changed (either from reset to set or 147 * the other way around), its respective meta dirty bitmap bit will be marked 148 * dirty as well. 149 * 150 * @bitmap: the block dirty bitmap for which to create a meta dirty bitmap. 151 * @chunk_size: how many bytes of bitmap data does each bit in the meta bitmap 152 * track. 153 */ 154 void bdrv_create_meta_dirty_bitmap(BdrvDirtyBitmap *bitmap, 155 int chunk_size) 156 { 157 assert(!bitmap->meta); 158 qemu_mutex_lock(bitmap->mutex); 159 bitmap->meta = hbitmap_create_meta(bitmap->bitmap, 160 chunk_size * BITS_PER_BYTE); 161 qemu_mutex_unlock(bitmap->mutex); 162 } 163 164 void bdrv_release_meta_dirty_bitmap(BdrvDirtyBitmap *bitmap) 165 { 166 assert(bitmap->meta); 167 qemu_mutex_lock(bitmap->mutex); 168 hbitmap_free_meta(bitmap->bitmap); 169 bitmap->meta = NULL; 170 qemu_mutex_unlock(bitmap->mutex); 171 } 172 173 int64_t bdrv_dirty_bitmap_size(const BdrvDirtyBitmap *bitmap) 174 { 175 return bitmap->size; 176 } 177 178 const char *bdrv_dirty_bitmap_name(const BdrvDirtyBitmap *bitmap) 179 { 180 return bitmap->name; 181 } 182 183 /* Called with BQL taken. */ 184 bool bdrv_dirty_bitmap_frozen(BdrvDirtyBitmap *bitmap) 185 { 186 return bitmap->successor; 187 } 188 189 /* Called with BQL taken. */ 190 bool bdrv_dirty_bitmap_enabled(BdrvDirtyBitmap *bitmap) 191 { 192 return !(bitmap->disabled || bitmap->successor); 193 } 194 195 /* Called with BQL taken. */ 196 DirtyBitmapStatus bdrv_dirty_bitmap_status(BdrvDirtyBitmap *bitmap) 197 { 198 if (bdrv_dirty_bitmap_frozen(bitmap)) { 199 return DIRTY_BITMAP_STATUS_FROZEN; 200 } else if (!bdrv_dirty_bitmap_enabled(bitmap)) { 201 return DIRTY_BITMAP_STATUS_DISABLED; 202 } else { 203 return DIRTY_BITMAP_STATUS_ACTIVE; 204 } 205 } 206 207 /** 208 * Create a successor bitmap destined to replace this bitmap after an operation. 209 * Requires that the bitmap is not frozen and has no successor. 210 * Called with BQL taken. 211 */ 212 int bdrv_dirty_bitmap_create_successor(BlockDriverState *bs, 213 BdrvDirtyBitmap *bitmap, Error **errp) 214 { 215 uint64_t granularity; 216 BdrvDirtyBitmap *child; 217 218 if (bdrv_dirty_bitmap_frozen(bitmap)) { 219 error_setg(errp, "Cannot create a successor for a bitmap that is " 220 "currently frozen"); 221 return -1; 222 } 223 assert(!bitmap->successor); 224 225 /* Create an anonymous successor */ 226 granularity = bdrv_dirty_bitmap_granularity(bitmap); 227 child = bdrv_create_dirty_bitmap(bs, granularity, NULL, errp); 228 if (!child) { 229 return -1; 230 } 231 232 /* Successor will be on or off based on our current state. */ 233 child->disabled = bitmap->disabled; 234 235 /* Install the successor and freeze the parent */ 236 bitmap->successor = child; 237 return 0; 238 } 239 240 /** 241 * For a bitmap with a successor, yield our name to the successor, 242 * delete the old bitmap, and return a handle to the new bitmap. 243 * Called with BQL taken. 244 */ 245 BdrvDirtyBitmap *bdrv_dirty_bitmap_abdicate(BlockDriverState *bs, 246 BdrvDirtyBitmap *bitmap, 247 Error **errp) 248 { 249 char *name; 250 BdrvDirtyBitmap *successor = bitmap->successor; 251 252 if (successor == NULL) { 253 error_setg(errp, "Cannot relinquish control if " 254 "there's no successor present"); 255 return NULL; 256 } 257 258 name = bitmap->name; 259 bitmap->name = NULL; 260 successor->name = name; 261 bitmap->successor = NULL; 262 successor->persistent = bitmap->persistent; 263 bitmap->persistent = false; 264 successor->autoload = bitmap->autoload; 265 bitmap->autoload = false; 266 bdrv_release_dirty_bitmap(bs, bitmap); 267 268 return successor; 269 } 270 271 /** 272 * In cases of failure where we can no longer safely delete the parent, 273 * we may wish to re-join the parent and child/successor. 274 * The merged parent will be un-frozen, but not explicitly re-enabled. 275 * Called with BQL taken. 276 */ 277 BdrvDirtyBitmap *bdrv_reclaim_dirty_bitmap(BlockDriverState *bs, 278 BdrvDirtyBitmap *parent, 279 Error **errp) 280 { 281 BdrvDirtyBitmap *successor = parent->successor; 282 283 if (!successor) { 284 error_setg(errp, "Cannot reclaim a successor when none is present"); 285 return NULL; 286 } 287 288 if (!hbitmap_merge(parent->bitmap, successor->bitmap)) { 289 error_setg(errp, "Merging of parent and successor bitmap failed"); 290 return NULL; 291 } 292 bdrv_release_dirty_bitmap(bs, successor); 293 parent->successor = NULL; 294 295 return parent; 296 } 297 298 /** 299 * Truncates _all_ bitmaps attached to a BDS. 300 * Called with BQL taken. 301 */ 302 void bdrv_dirty_bitmap_truncate(BlockDriverState *bs, int64_t bytes) 303 { 304 BdrvDirtyBitmap *bitmap; 305 306 bdrv_dirty_bitmaps_lock(bs); 307 QLIST_FOREACH(bitmap, &bs->dirty_bitmaps, list) { 308 assert(!bdrv_dirty_bitmap_frozen(bitmap)); 309 assert(!bitmap->active_iterators); 310 hbitmap_truncate(bitmap->bitmap, bytes); 311 bitmap->size = bytes; 312 } 313 bdrv_dirty_bitmaps_unlock(bs); 314 } 315 316 static bool bdrv_dirty_bitmap_has_name(BdrvDirtyBitmap *bitmap) 317 { 318 return !!bdrv_dirty_bitmap_name(bitmap); 319 } 320 321 /* Called with BQL taken. */ 322 static void bdrv_do_release_matching_dirty_bitmap( 323 BlockDriverState *bs, BdrvDirtyBitmap *bitmap, 324 bool (*cond)(BdrvDirtyBitmap *bitmap)) 325 { 326 BdrvDirtyBitmap *bm, *next; 327 bdrv_dirty_bitmaps_lock(bs); 328 QLIST_FOREACH_SAFE(bm, &bs->dirty_bitmaps, list, next) { 329 if ((!bitmap || bm == bitmap) && (!cond || cond(bm))) { 330 assert(!bm->active_iterators); 331 assert(!bdrv_dirty_bitmap_frozen(bm)); 332 assert(!bm->meta); 333 QLIST_REMOVE(bm, list); 334 hbitmap_free(bm->bitmap); 335 g_free(bm->name); 336 g_free(bm); 337 338 if (bitmap) { 339 goto out; 340 } 341 } 342 } 343 if (bitmap) { 344 abort(); 345 } 346 347 out: 348 bdrv_dirty_bitmaps_unlock(bs); 349 } 350 351 /* Called with BQL taken. */ 352 void bdrv_release_dirty_bitmap(BlockDriverState *bs, BdrvDirtyBitmap *bitmap) 353 { 354 bdrv_do_release_matching_dirty_bitmap(bs, bitmap, NULL); 355 } 356 357 /** 358 * Release all named dirty bitmaps attached to a BDS (for use in bdrv_close()). 359 * There must not be any frozen bitmaps attached. 360 * This function does not remove persistent bitmaps from the storage. 361 * Called with BQL taken. 362 */ 363 void bdrv_release_named_dirty_bitmaps(BlockDriverState *bs) 364 { 365 bdrv_do_release_matching_dirty_bitmap(bs, NULL, bdrv_dirty_bitmap_has_name); 366 } 367 368 /** 369 * Release all persistent dirty bitmaps attached to a BDS (for use in 370 * bdrv_inactivate_recurse()). 371 * There must not be any frozen bitmaps attached. 372 * This function does not remove persistent bitmaps from the storage. 373 */ 374 void bdrv_release_persistent_dirty_bitmaps(BlockDriverState *bs) 375 { 376 bdrv_do_release_matching_dirty_bitmap(bs, NULL, 377 bdrv_dirty_bitmap_get_persistance); 378 } 379 380 /** 381 * Remove persistent dirty bitmap from the storage if it exists. 382 * Absence of bitmap is not an error, because we have the following scenario: 383 * BdrvDirtyBitmap can have .persistent = true but not yet saved and have no 384 * stored version. For such bitmap bdrv_remove_persistent_dirty_bitmap() should 385 * not fail. 386 * This function doesn't release corresponding BdrvDirtyBitmap. 387 */ 388 void bdrv_remove_persistent_dirty_bitmap(BlockDriverState *bs, 389 const char *name, 390 Error **errp) 391 { 392 if (bs->drv && bs->drv->bdrv_remove_persistent_dirty_bitmap) { 393 bs->drv->bdrv_remove_persistent_dirty_bitmap(bs, name, errp); 394 } 395 } 396 397 /* Called with BQL taken. */ 398 void bdrv_disable_dirty_bitmap(BdrvDirtyBitmap *bitmap) 399 { 400 assert(!bdrv_dirty_bitmap_frozen(bitmap)); 401 bitmap->disabled = true; 402 } 403 404 /* Called with BQL taken. */ 405 void bdrv_enable_dirty_bitmap(BdrvDirtyBitmap *bitmap) 406 { 407 assert(!bdrv_dirty_bitmap_frozen(bitmap)); 408 bitmap->disabled = false; 409 } 410 411 BlockDirtyInfoList *bdrv_query_dirty_bitmaps(BlockDriverState *bs) 412 { 413 BdrvDirtyBitmap *bm; 414 BlockDirtyInfoList *list = NULL; 415 BlockDirtyInfoList **plist = &list; 416 417 bdrv_dirty_bitmaps_lock(bs); 418 QLIST_FOREACH(bm, &bs->dirty_bitmaps, list) { 419 BlockDirtyInfo *info = g_new0(BlockDirtyInfo, 1); 420 BlockDirtyInfoList *entry = g_new0(BlockDirtyInfoList, 1); 421 info->count = bdrv_get_dirty_count(bm); 422 info->granularity = bdrv_dirty_bitmap_granularity(bm); 423 info->has_name = !!bm->name; 424 info->name = g_strdup(bm->name); 425 info->status = bdrv_dirty_bitmap_status(bm); 426 entry->value = info; 427 *plist = entry; 428 plist = &entry->next; 429 } 430 bdrv_dirty_bitmaps_unlock(bs); 431 432 return list; 433 } 434 435 /* Called within bdrv_dirty_bitmap_lock..unlock */ 436 bool bdrv_get_dirty_locked(BlockDriverState *bs, BdrvDirtyBitmap *bitmap, 437 int64_t offset) 438 { 439 if (bitmap) { 440 return hbitmap_get(bitmap->bitmap, offset); 441 } else { 442 return false; 443 } 444 } 445 446 /** 447 * Chooses a default granularity based on the existing cluster size, 448 * but clamped between [4K, 64K]. Defaults to 64K in the case that there 449 * is no cluster size information available. 450 */ 451 uint32_t bdrv_get_default_bitmap_granularity(BlockDriverState *bs) 452 { 453 BlockDriverInfo bdi; 454 uint32_t granularity; 455 456 if (bdrv_get_info(bs, &bdi) >= 0 && bdi.cluster_size > 0) { 457 granularity = MAX(4096, bdi.cluster_size); 458 granularity = MIN(65536, granularity); 459 } else { 460 granularity = 65536; 461 } 462 463 return granularity; 464 } 465 466 uint32_t bdrv_dirty_bitmap_granularity(const BdrvDirtyBitmap *bitmap) 467 { 468 return 1U << hbitmap_granularity(bitmap->bitmap); 469 } 470 471 BdrvDirtyBitmapIter *bdrv_dirty_iter_new(BdrvDirtyBitmap *bitmap) 472 { 473 BdrvDirtyBitmapIter *iter = g_new(BdrvDirtyBitmapIter, 1); 474 hbitmap_iter_init(&iter->hbi, bitmap->bitmap, 0); 475 iter->bitmap = bitmap; 476 bitmap->active_iterators++; 477 return iter; 478 } 479 480 BdrvDirtyBitmapIter *bdrv_dirty_meta_iter_new(BdrvDirtyBitmap *bitmap) 481 { 482 BdrvDirtyBitmapIter *iter = g_new(BdrvDirtyBitmapIter, 1); 483 hbitmap_iter_init(&iter->hbi, bitmap->meta, 0); 484 iter->bitmap = bitmap; 485 bitmap->active_iterators++; 486 return iter; 487 } 488 489 void bdrv_dirty_iter_free(BdrvDirtyBitmapIter *iter) 490 { 491 if (!iter) { 492 return; 493 } 494 assert(iter->bitmap->active_iterators > 0); 495 iter->bitmap->active_iterators--; 496 g_free(iter); 497 } 498 499 int64_t bdrv_dirty_iter_next(BdrvDirtyBitmapIter *iter) 500 { 501 return hbitmap_iter_next(&iter->hbi); 502 } 503 504 /* Called within bdrv_dirty_bitmap_lock..unlock */ 505 void bdrv_set_dirty_bitmap_locked(BdrvDirtyBitmap *bitmap, 506 int64_t offset, int64_t bytes) 507 { 508 assert(bdrv_dirty_bitmap_enabled(bitmap)); 509 assert(!bdrv_dirty_bitmap_readonly(bitmap)); 510 hbitmap_set(bitmap->bitmap, offset, bytes); 511 } 512 513 void bdrv_set_dirty_bitmap(BdrvDirtyBitmap *bitmap, 514 int64_t offset, int64_t bytes) 515 { 516 bdrv_dirty_bitmap_lock(bitmap); 517 bdrv_set_dirty_bitmap_locked(bitmap, offset, bytes); 518 bdrv_dirty_bitmap_unlock(bitmap); 519 } 520 521 /* Called within bdrv_dirty_bitmap_lock..unlock */ 522 void bdrv_reset_dirty_bitmap_locked(BdrvDirtyBitmap *bitmap, 523 int64_t offset, int64_t bytes) 524 { 525 assert(bdrv_dirty_bitmap_enabled(bitmap)); 526 assert(!bdrv_dirty_bitmap_readonly(bitmap)); 527 hbitmap_reset(bitmap->bitmap, offset, bytes); 528 } 529 530 void bdrv_reset_dirty_bitmap(BdrvDirtyBitmap *bitmap, 531 int64_t offset, int64_t bytes) 532 { 533 bdrv_dirty_bitmap_lock(bitmap); 534 bdrv_reset_dirty_bitmap_locked(bitmap, offset, bytes); 535 bdrv_dirty_bitmap_unlock(bitmap); 536 } 537 538 void bdrv_clear_dirty_bitmap(BdrvDirtyBitmap *bitmap, HBitmap **out) 539 { 540 assert(bdrv_dirty_bitmap_enabled(bitmap)); 541 assert(!bdrv_dirty_bitmap_readonly(bitmap)); 542 bdrv_dirty_bitmap_lock(bitmap); 543 if (!out) { 544 hbitmap_reset_all(bitmap->bitmap); 545 } else { 546 HBitmap *backup = bitmap->bitmap; 547 bitmap->bitmap = hbitmap_alloc(bitmap->size, 548 hbitmap_granularity(backup)); 549 *out = backup; 550 } 551 bdrv_dirty_bitmap_unlock(bitmap); 552 } 553 554 void bdrv_undo_clear_dirty_bitmap(BdrvDirtyBitmap *bitmap, HBitmap *in) 555 { 556 HBitmap *tmp = bitmap->bitmap; 557 assert(bdrv_dirty_bitmap_enabled(bitmap)); 558 assert(!bdrv_dirty_bitmap_readonly(bitmap)); 559 bitmap->bitmap = in; 560 hbitmap_free(tmp); 561 } 562 563 uint64_t bdrv_dirty_bitmap_serialization_size(const BdrvDirtyBitmap *bitmap, 564 uint64_t offset, uint64_t bytes) 565 { 566 return hbitmap_serialization_size(bitmap->bitmap, offset, bytes); 567 } 568 569 uint64_t bdrv_dirty_bitmap_serialization_align(const BdrvDirtyBitmap *bitmap) 570 { 571 return hbitmap_serialization_align(bitmap->bitmap); 572 } 573 574 void bdrv_dirty_bitmap_serialize_part(const BdrvDirtyBitmap *bitmap, 575 uint8_t *buf, uint64_t offset, 576 uint64_t bytes) 577 { 578 hbitmap_serialize_part(bitmap->bitmap, buf, offset, bytes); 579 } 580 581 void bdrv_dirty_bitmap_deserialize_part(BdrvDirtyBitmap *bitmap, 582 uint8_t *buf, uint64_t offset, 583 uint64_t bytes, bool finish) 584 { 585 hbitmap_deserialize_part(bitmap->bitmap, buf, offset, bytes, finish); 586 } 587 588 void bdrv_dirty_bitmap_deserialize_zeroes(BdrvDirtyBitmap *bitmap, 589 uint64_t offset, uint64_t bytes, 590 bool finish) 591 { 592 hbitmap_deserialize_zeroes(bitmap->bitmap, offset, bytes, finish); 593 } 594 595 void bdrv_dirty_bitmap_deserialize_ones(BdrvDirtyBitmap *bitmap, 596 uint64_t offset, uint64_t bytes, 597 bool finish) 598 { 599 hbitmap_deserialize_ones(bitmap->bitmap, offset, bytes, finish); 600 } 601 602 void bdrv_dirty_bitmap_deserialize_finish(BdrvDirtyBitmap *bitmap) 603 { 604 hbitmap_deserialize_finish(bitmap->bitmap); 605 } 606 607 void bdrv_set_dirty(BlockDriverState *bs, int64_t offset, int64_t bytes) 608 { 609 BdrvDirtyBitmap *bitmap; 610 611 if (QLIST_EMPTY(&bs->dirty_bitmaps)) { 612 return; 613 } 614 615 bdrv_dirty_bitmaps_lock(bs); 616 QLIST_FOREACH(bitmap, &bs->dirty_bitmaps, list) { 617 if (!bdrv_dirty_bitmap_enabled(bitmap)) { 618 continue; 619 } 620 assert(!bdrv_dirty_bitmap_readonly(bitmap)); 621 hbitmap_set(bitmap->bitmap, offset, bytes); 622 } 623 bdrv_dirty_bitmaps_unlock(bs); 624 } 625 626 /** 627 * Advance a BdrvDirtyBitmapIter to an arbitrary offset. 628 */ 629 void bdrv_set_dirty_iter(BdrvDirtyBitmapIter *iter, int64_t offset) 630 { 631 hbitmap_iter_init(&iter->hbi, iter->hbi.hb, offset); 632 } 633 634 int64_t bdrv_get_dirty_count(BdrvDirtyBitmap *bitmap) 635 { 636 return hbitmap_count(bitmap->bitmap); 637 } 638 639 int64_t bdrv_get_meta_dirty_count(BdrvDirtyBitmap *bitmap) 640 { 641 return hbitmap_count(bitmap->meta); 642 } 643 644 bool bdrv_dirty_bitmap_readonly(const BdrvDirtyBitmap *bitmap) 645 { 646 return bitmap->readonly; 647 } 648 649 /* Called with BQL taken. */ 650 void bdrv_dirty_bitmap_set_readonly(BdrvDirtyBitmap *bitmap, bool value) 651 { 652 qemu_mutex_lock(bitmap->mutex); 653 bitmap->readonly = value; 654 qemu_mutex_unlock(bitmap->mutex); 655 } 656 657 bool bdrv_has_readonly_bitmaps(BlockDriverState *bs) 658 { 659 BdrvDirtyBitmap *bm; 660 QLIST_FOREACH(bm, &bs->dirty_bitmaps, list) { 661 if (bm->readonly) { 662 return true; 663 } 664 } 665 666 return false; 667 } 668 669 /* Called with BQL taken. */ 670 void bdrv_dirty_bitmap_set_autoload(BdrvDirtyBitmap *bitmap, bool autoload) 671 { 672 qemu_mutex_lock(bitmap->mutex); 673 bitmap->autoload = autoload; 674 qemu_mutex_unlock(bitmap->mutex); 675 } 676 677 bool bdrv_dirty_bitmap_get_autoload(const BdrvDirtyBitmap *bitmap) 678 { 679 return bitmap->autoload; 680 } 681 682 /* Called with BQL taken. */ 683 void bdrv_dirty_bitmap_set_persistance(BdrvDirtyBitmap *bitmap, bool persistent) 684 { 685 qemu_mutex_lock(bitmap->mutex); 686 bitmap->persistent = persistent; 687 qemu_mutex_unlock(bitmap->mutex); 688 } 689 690 bool bdrv_dirty_bitmap_get_persistance(BdrvDirtyBitmap *bitmap) 691 { 692 return bitmap->persistent; 693 } 694 695 bool bdrv_has_changed_persistent_bitmaps(BlockDriverState *bs) 696 { 697 BdrvDirtyBitmap *bm; 698 QLIST_FOREACH(bm, &bs->dirty_bitmaps, list) { 699 if (bm->persistent && !bm->readonly) { 700 return true; 701 } 702 } 703 704 return false; 705 } 706 707 BdrvDirtyBitmap *bdrv_dirty_bitmap_next(BlockDriverState *bs, 708 BdrvDirtyBitmap *bitmap) 709 { 710 return bitmap == NULL ? QLIST_FIRST(&bs->dirty_bitmaps) : 711 QLIST_NEXT(bitmap, list); 712 } 713 714 char *bdrv_dirty_bitmap_sha256(const BdrvDirtyBitmap *bitmap, Error **errp) 715 { 716 return hbitmap_sha256(bitmap->bitmap, errp); 717 } 718