diff options
Diffstat (limited to 'sys/contrib/openzfs/include/sys/abd.h')
-rw-r--r-- | sys/contrib/openzfs/include/sys/abd.h | 75 |
1 files changed, 67 insertions, 8 deletions
diff --git a/sys/contrib/openzfs/include/sys/abd.h b/sys/contrib/openzfs/include/sys/abd.h index 735a13147598..a7eee89ca916 100644 --- a/sys/contrib/openzfs/include/sys/abd.h +++ b/sys/contrib/openzfs/include/sys/abd.h @@ -35,8 +35,48 @@ extern "C" { #endif -struct abd; /* forward declaration */ -typedef struct abd abd_t; +typedef enum abd_flags { + ABD_FLAG_LINEAR = 1 << 0, /* is buffer linear (or scattered)? */ + ABD_FLAG_OWNER = 1 << 1, /* does it own its data buffers? */ + ABD_FLAG_META = 1 << 2, /* does this represent FS metadata? */ + ABD_FLAG_MULTI_ZONE = 1 << 3, /* pages split over memory zones */ + ABD_FLAG_MULTI_CHUNK = 1 << 4, /* pages split over multiple chunks */ + ABD_FLAG_LINEAR_PAGE = 1 << 5, /* linear but allocd from page */ + ABD_FLAG_GANG = 1 << 6, /* mult ABDs chained together */ + ABD_FLAG_GANG_FREE = 1 << 7, /* gang ABD is responsible for mem */ + ABD_FLAG_ZEROS = 1 << 8, /* ABD for zero-filled buffer */ + ABD_FLAG_ALLOCD = 1 << 9, /* we allocated the abd_t */ +} abd_flags_t; + +typedef struct abd { + abd_flags_t abd_flags; + uint_t abd_size; /* excludes scattered abd_offset */ + list_node_t abd_gang_link; +#ifdef ZFS_DEBUG + struct abd *abd_parent; + zfs_refcount_t abd_children; +#endif + kmutex_t abd_mtx; + union { + struct abd_scatter { + uint_t abd_offset; +#if defined(__FreeBSD__) && defined(_KERNEL) + uint_t abd_chunk_size; + void *abd_chunks[1]; /* actually variable-length */ +#else + uint_t abd_nents; + struct scatterlist *abd_sgl; +#endif + } abd_scatter; + struct abd_linear { + void *abd_buf; + struct scatterlist *abd_sgl; /* for LINEAR_PAGE */ + } abd_linear; + struct abd_gang { + list_t abd_gang_chain; + } abd_gang; + } abd_u; +} abd_t; typedef int abd_iter_func_t(void *buf, size_t len, void *priv); typedef int abd_iter_func2_t(void *bufa, void *bufb, size_t len, void *priv); @@ -49,14 +89,14 @@ extern int zfs_abd_scatter_enabled; abd_t *abd_alloc(size_t, boolean_t); abd_t *abd_alloc_linear(size_t, boolean_t); -abd_t *abd_alloc_gang_abd(void); +abd_t *abd_alloc_gang(void); abd_t *abd_alloc_for_io(size_t, boolean_t); abd_t *abd_alloc_sametype(abd_t *, size_t); void abd_gang_add(abd_t *, abd_t *, boolean_t); void abd_free(abd_t *); -void abd_put(abd_t *); abd_t *abd_get_offset(abd_t *, size_t); abd_t *abd_get_offset_size(abd_t *, size_t, size_t); +abd_t *abd_get_offset_struct(abd_t *, abd_t *, size_t, size_t); abd_t *abd_get_zeros(size_t); abd_t *abd_get_from_buf(void *, size_t); void abd_cache_reap_now(void); @@ -87,7 +127,6 @@ int abd_cmp(abd_t *, abd_t *); int abd_cmp_buf_off(abd_t *, const void *, size_t, size_t); void abd_zero_off(abd_t *, size_t, size_t); void abd_verify(abd_t *); -uint_t abd_get_size(abd_t *); void abd_raidz_gen_iterate(abd_t **cabds, abd_t *dabd, ssize_t csize, ssize_t dsize, const unsigned parity, @@ -135,9 +174,29 @@ abd_zero(abd_t *abd, size_t size) /* * ABD type check functions */ -boolean_t abd_is_linear(abd_t *); -boolean_t abd_is_gang(abd_t *); -boolean_t abd_is_linear_page(abd_t *); +static inline boolean_t +abd_is_linear(abd_t *abd) +{ + return ((abd->abd_flags & ABD_FLAG_LINEAR) ? B_TRUE : B_FALSE); +} + +static inline boolean_t +abd_is_linear_page(abd_t *abd) +{ + return ((abd->abd_flags & ABD_FLAG_LINEAR_PAGE) ? B_TRUE : B_FALSE); +} + +static inline boolean_t +abd_is_gang(abd_t *abd) +{ + return ((abd->abd_flags & ABD_FLAG_GANG) ? B_TRUE : B_FALSE); +} + +static inline uint_t +abd_get_size(abd_t *abd) +{ + return (abd->abd_size); +} /* * Module lifecycle |