vdisk_fileio, async mode: Support multi-page sgv's for kernels < v5.1

This commit is contained in:
Chesnokov Gleb
2021-12-08 21:44:58 +03:00
committed by Gleb Chesnokov
parent 414805bb4d
commit a08e8b8b35
2 changed files with 59 additions and 5 deletions
+17
View File
@@ -5133,6 +5133,23 @@ static inline int scst_get_buf_count(struct scst_cmd *cmd)
return (cmd->sg_cnt == 0) ? 1 : cmd->sg_cnt;
}
/*
* Returns approximate higher rounded buffers count in pages
*/
static inline int scst_get_buf_page_count(struct scst_cmd *cmd)
{
struct scatterlist *sg;
int page_cnt = 0, i;
if (unlikely(cmd->sg_cnt == 0))
return 1;
for (i = 0, sg = cmd->sg; i < cmd->sg_cnt; i++, sg = sg_next_inline(sg))
page_cnt += PAGE_ALIGN(sg->offset + sg->length) >> PAGE_SHIFT;
return page_cnt;
}
/*
* Returns approximate higher rounded buffers count that
* scst_get_out_buf_[first|next]() return.
+42 -5
View File
@@ -3175,7 +3175,11 @@ static bool vdisk_alloc_async_bvec(struct scst_cmd *cmd,
{
int n;
#if LINUX_VERSION_CODE < KERNEL_VERSION(5, 1, 0)
n = scst_get_buf_page_count(cmd);
#else
n = scst_get_buf_count(cmd);
#endif
if (n <= ARRAY_SIZE(p->async.small_bvec)) {
p->async.bvec = &p->async.small_bvec[0];
return true;
@@ -3191,6 +3195,42 @@ static bool vdisk_alloc_async_bvec(struct scst_cmd *cmd,
return true;
}
static inline
struct bio_vec *vdisk_map_pages_to_bvec(struct bio_vec *bvec, struct page *page,
ssize_t length, int offset)
{
#if LINUX_VERSION_CODE < KERNEL_VERSION(5, 1, 0)
ssize_t page_len = min_t(ssize_t, length, PAGE_SIZE - offset);
#else
ssize_t page_len = length;
#endif
*bvec++ = (struct bio_vec) {
.bv_page = page,
.bv_offset = offset,
.bv_len = page_len,
};
#if LINUX_VERSION_CODE < KERNEL_VERSION(5, 1, 0)
length -= page_len;
while (length > 0) {
page++;
page_len = min_t(ssize_t, length, PAGE_SIZE);
*bvec++ = (struct bio_vec) {
.bv_page = page,
.bv_offset = 0,
.bv_len = page_len,
};
length -= page_len;
}
#endif
return bvec;
}
static void fileio_async_complete(struct kiocb *iocb, long ret
#if LINUX_VERSION_CODE < KERNEL_VERSION(5, 16, 0)
, long ret2
@@ -3262,11 +3302,8 @@ static enum compl_status_e fileio_exec_async(struct vdisk_cmd_params *p)
bvec = p->async.bvec;
length = scst_get_sg_page_first(cmd, &page, &offset);
while (length) {
*bvec++ = (struct bio_vec){
.bv_page = page,
.bv_offset = offset,
.bv_len = length,
};
bvec = vdisk_map_pages_to_bvec(bvec, page, length, offset);
total += length;
sg_cnt++;
length = scst_get_sg_page_next(cmd, &page, &offset);