Skip to content

Commit 6b67a5b

Browse files
don-bradybehlendorf
authored andcommitted
During pool export flush the ARC asynchronously
This also includes removing L2 vdevs asynchronously. This commit also guarantees that spa_load_guid is unique. The zpool reguid feature introduced the spa_load_guid, which is a transient value used for runtime identification purposes in the ARC. This value is not the same as the spa's persistent pool guid. However, the value is seeded from spa_generate_load_guid() which does not check for uniqueness against the spa_load_guid from other pools. Although extremely rare, you can end up with two different pools sharing the same spa_load_guid value! So we guarantee that the value is always unique and additionally not still in use by an async arc flush task. Sponsored-by: Klara, Inc. Sponsored-by: Wasabi Technology, Inc. Reviewed-by: Brian Behlendorf <[email protected]> Reviewed-by: Alexander Motin <[email protected]> Reviewed-by: Allan Jude <[email protected]> Signed-off-by: Don Brady <[email protected]> Closes openzfs#16215
1 parent 4f1b91e commit 6b67a5b

File tree

7 files changed

+325
-66
lines changed

7 files changed

+325
-66
lines changed

include/sys/arc.h

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,8 +64,15 @@ extern "C" {
6464
(hdr)->b_psize = ((x) >> SPA_MINBLOCKSHIFT); \
6565
} while (0)
6666

67+
/* The l2size in the header is only used by L2 cache */
68+
#define HDR_SET_L2SIZE(hdr, x) do { \
69+
ASSERT(IS_P2ALIGNED((x), 1U << SPA_MINBLOCKSHIFT)); \
70+
(hdr)->b_l2size = ((x) >> SPA_MINBLOCKSHIFT); \
71+
} while (0)
72+
6773
#define HDR_GET_LSIZE(hdr) ((hdr)->b_lsize << SPA_MINBLOCKSHIFT)
6874
#define HDR_GET_PSIZE(hdr) ((hdr)->b_psize << SPA_MINBLOCKSHIFT)
75+
#define HDR_GET_L2SIZE(hdr) ((hdr)->b_l2size << SPA_MINBLOCKSHIFT)
6976

7077
typedef struct arc_buf_hdr arc_buf_hdr_t;
7178
typedef struct arc_buf arc_buf_t;
@@ -323,8 +330,10 @@ void arc_freed(spa_t *spa, const blkptr_t *bp);
323330
int arc_cached(spa_t *spa, const blkptr_t *bp);
324331

325332
void arc_flush(spa_t *spa, boolean_t retry);
333+
void arc_flush_async(spa_t *spa);
326334
void arc_tempreserve_clear(uint64_t reserve);
327335
int arc_tempreserve_space(spa_t *spa, uint64_t reserve, uint64_t txg);
336+
boolean_t arc_async_flush_guid_inuse(uint64_t load_guid);
328337

329338
uint64_t arc_all_memory(void);
330339
uint64_t arc_default_max(uint64_t min, uint64_t allmem);

include/sys/arc_impl.h

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -379,8 +379,8 @@ typedef struct l2arc_lb_ptr_buf {
379379
* L2ARC Internals
380380
*/
381381
typedef struct l2arc_dev {
382-
vdev_t *l2ad_vdev; /* vdev */
383-
spa_t *l2ad_spa; /* spa */
382+
vdev_t *l2ad_vdev; /* can be NULL during remove */
383+
spa_t *l2ad_spa; /* can be NULL during remove */
384384
uint64_t l2ad_hand; /* next write location */
385385
uint64_t l2ad_start; /* first addr on device */
386386
uint64_t l2ad_end; /* last addr on device */
@@ -476,8 +476,8 @@ struct arc_buf_hdr {
476476

477477
arc_buf_contents_t b_type;
478478
uint8_t b_complevel;
479-
uint8_t b_reserved1; /* used for 4 byte alignment */
480-
uint16_t b_reserved2; /* used for 4 byte alignment */
479+
uint8_t b_reserved1; /* used for 4 byte alignment */
480+
uint16_t b_l2size; /* alignment or L2-only size */
481481
arc_buf_hdr_t *b_hash_next;
482482
arc_flags_t b_flags;
483483

include/sys/spa.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1103,6 +1103,7 @@ extern boolean_t spa_guid_exists(uint64_t pool_guid, uint64_t device_guid);
11031103
extern char *spa_strdup(const char *);
11041104
extern void spa_strfree(char *);
11051105
extern uint64_t spa_generate_guid(spa_t *spa);
1106+
extern uint64_t spa_generate_load_guid(void);
11061107
extern void snprintf_blkptr(char *buf, size_t buflen, const blkptr_t *bp);
11071108
extern void spa_freeze(spa_t *spa);
11081109
extern int spa_change_guid(spa_t *spa, const uint64_t *guidp);

0 commit comments

Comments
 (0)