[PATCH 10/11] lib/scatterlist: Add and export sg_trim_table

Tvrtko Ursulin tursulin at ursulin.net
Fri Mar 2 10:55:05 UTC 2018


From: Tvrtko Ursulin <tvrtko.ursulin at intel.com>

Drivers like i915 can benefit from using the newly added scatterlist
library internal code which "trims" the sg table to the exact required
size.

Export this API so drivers are able to use it.

Signed-off-by: Tvrtko Ursulin <tvrtko.ursulin at intel.com>
Cc: Bart Van Assche <bart.vanassche at wdc.com>
Cc: Hannes Reinecke <hare at suse.com>
Cc: Johannes Thumshirn <jthumshirn at suse.de>
Cc: Jens Axboe <axboe at kernel.dk>
---
 include/linux/scatterlist.h |  2 ++
 lib/scatterlist.c           | 26 ++++++++++++++++++++++++++
 2 files changed, 28 insertions(+)

diff --git a/include/linux/scatterlist.h b/include/linux/scatterlist.h
index 983a8391d469..46edc9967c74 100644
--- a/include/linux/scatterlist.h
+++ b/include/linux/scatterlist.h
@@ -276,6 +276,8 @@ int sg_alloc_table_from_pages(struct sg_table *sgt, struct page **pages,
 			      unsigned int n_pages, unsigned int offset,
 			      unsigned long size, gfp_t gfp_mask);
 
+void sg_trim_table(struct sg_table *st, gfp_t gfp);
+
 #ifdef CONFIG_SGL_ALLOC
 struct scatterlist *
 sgl_alloc_order_min_max(unsigned long length,
diff --git a/lib/scatterlist.c b/lib/scatterlist.c
index 24c9ca5110b9..b6103898a7b2 100644
--- a/lib/scatterlist.c
+++ b/lib/scatterlist.c
@@ -555,6 +555,32 @@ __sg_trim_scatterlist(struct scatterlist *sg,
 	return new;
 }
 
+/**
+ * sg_trim_table - Reallocate the table for minimum scatterlist size
+ *
+ * @st: 	Existing table.
+ * @gfp: 	Allocation flags to use when re-allocating.
+ *
+ * This function reallocates the scatterlist table if the orig_nents is larger
+ * than nents.
+ *
+ * This is useful for avoiding memory waste in cases when lists are built
+ * dynamically, the minimum number of entries is not known before hand, and the
+ * two pass approach is not feasible.
+ */
+void sg_trim_table(struct sg_table *st, gfp_t gfp)
+{
+	struct scatterlist *sg;
+
+	sg = __sg_trim_scatterlist(st->sgl, st->nents, st->orig_nents, gfp);
+
+	if (sg && sg != st->sgl) {
+		st->sgl = sg;
+		st->orig_nents = st->nents;
+	}
+}
+EXPORT_SYMBOL(sg_trim_table);
+
 struct scatterlist *
 sgl_alloc_order_min_max(unsigned long length,
 			unsigned int min_order, unsigned int max_order,
-- 
2.14.1



More information about the Intel-gfx-trybot mailing list