diff options
Diffstat (limited to 'include')
-rw-r--r-- | include/linux/scatterlist.h | 49 |
1 files changed, 40 insertions, 9 deletions
diff --git a/include/linux/scatterlist.h b/include/linux/scatterlist.h index b96f0d0b5b8f..b4be960c7e5d 100644 --- a/include/linux/scatterlist.h +++ b/include/linux/scatterlist.h | |||
@@ -339,12 +339,12 @@ int sg_alloc_table_chained(struct sg_table *table, int nents, | |||
339 | /* | 339 | /* |
340 | * sg page iterator | 340 | * sg page iterator |
341 | * | 341 | * |
342 | * Iterates over sg entries page-by-page. On each successful iteration, | 342 | * Iterates over sg entries page-by-page. On each successful iteration, you |
343 | * you can call sg_page_iter_page(@piter) and sg_page_iter_dma_address(@piter) | 343 | * can call sg_page_iter_page(@piter) to get the current page and its dma |
344 | * to get the current page and its dma address. @piter->sg will point to the | 344 | * address. @piter->sg will point to the sg holding this page and |
345 | * sg holding this page and @piter->sg_pgoffset to the page's page offset | 345 | * @piter->sg_pgoffset to the page's page offset within the sg. The iteration |
346 | * within the sg. The iteration will stop either when a maximum number of sg | 346 | * will stop either when a maximum number of sg entries was reached or a |
347 | * entries was reached or a terminating sg (sg_last(sg) == true) was reached. | 347 | * terminating sg (sg_last(sg) == true) was reached. |
348 | */ | 348 | */ |
349 | struct sg_page_iter { | 349 | struct sg_page_iter { |
350 | struct scatterlist *sg; /* sg holding the page */ | 350 | struct scatterlist *sg; /* sg holding the page */ |
@@ -356,7 +356,19 @@ struct sg_page_iter { | |||
356 | * next step */ | 356 | * next step */ |
357 | }; | 357 | }; |
358 | 358 | ||
359 | /* | ||
360 | * sg page iterator for DMA addresses | ||
361 | * | ||
362 | * This is the same as sg_page_iter however you can call | ||
363 | * sg_page_iter_dma_address(@dma_iter) to get the page's DMA | ||
364 | * address. sg_page_iter_page() cannot be called on this iterator. | ||
365 | */ | ||
366 | struct sg_dma_page_iter { | ||
367 | struct sg_page_iter base; | ||
368 | }; | ||
369 | |||
359 | bool __sg_page_iter_next(struct sg_page_iter *piter); | 370 | bool __sg_page_iter_next(struct sg_page_iter *piter); |
371 | bool __sg_page_iter_dma_next(struct sg_dma_page_iter *dma_iter); | ||
360 | void __sg_page_iter_start(struct sg_page_iter *piter, | 372 | void __sg_page_iter_start(struct sg_page_iter *piter, |
361 | struct scatterlist *sglist, unsigned int nents, | 373 | struct scatterlist *sglist, unsigned int nents, |
362 | unsigned long pgoffset); | 374 | unsigned long pgoffset); |
@@ -372,11 +384,13 @@ static inline struct page *sg_page_iter_page(struct sg_page_iter *piter) | |||
372 | /** | 384 | /** |
373 | * sg_page_iter_dma_address - get the dma address of the current page held by | 385 | * sg_page_iter_dma_address - get the dma address of the current page held by |
374 | * the page iterator. | 386 | * the page iterator. |
375 | * @piter: page iterator holding the page | 387 | * @dma_iter: page iterator holding the page |
376 | */ | 388 | */ |
377 | static inline dma_addr_t sg_page_iter_dma_address(struct sg_page_iter *piter) | 389 | static inline dma_addr_t |
390 | sg_page_iter_dma_address(struct sg_dma_page_iter *dma_iter) | ||
378 | { | 391 | { |
379 | return sg_dma_address(piter->sg) + (piter->sg_pgoffset << PAGE_SHIFT); | 392 | return sg_dma_address(dma_iter->base.sg) + |
393 | (dma_iter->base.sg_pgoffset << PAGE_SHIFT); | ||
380 | } | 394 | } |
381 | 395 | ||
382 | /** | 396 | /** |
@@ -385,11 +399,28 @@ static inline dma_addr_t sg_page_iter_dma_address(struct sg_page_iter *piter) | |||
385 | * @piter: page iterator to hold current page, sg, sg_pgoffset | 399 | * @piter: page iterator to hold current page, sg, sg_pgoffset |
386 | * @nents: maximum number of sg entries to iterate over | 400 | * @nents: maximum number of sg entries to iterate over |
387 | * @pgoffset: starting page offset | 401 | * @pgoffset: starting page offset |
402 | * | ||
403 | * Callers may use sg_page_iter_page() to get each page pointer. | ||
388 | */ | 404 | */ |
389 | #define for_each_sg_page(sglist, piter, nents, pgoffset) \ | 405 | #define for_each_sg_page(sglist, piter, nents, pgoffset) \ |
390 | for (__sg_page_iter_start((piter), (sglist), (nents), (pgoffset)); \ | 406 | for (__sg_page_iter_start((piter), (sglist), (nents), (pgoffset)); \ |
391 | __sg_page_iter_next(piter);) | 407 | __sg_page_iter_next(piter);) |
392 | 408 | ||
409 | /** | ||
410 | * for_each_sg_dma_page - iterate over the pages of the given sg list | ||
411 | * @sglist: sglist to iterate over | ||
412 | * @dma_iter: page iterator to hold current page | ||
413 | * @dma_nents: maximum number of sg entries to iterate over, this is the value | ||
414 | * returned from dma_map_sg | ||
415 | * @pgoffset: starting page offset | ||
416 | * | ||
417 | * Callers may use sg_page_iter_dma_address() to get each page's DMA address. | ||
418 | */ | ||
419 | #define for_each_sg_dma_page(sglist, dma_iter, dma_nents, pgoffset) \ | ||
420 | for (__sg_page_iter_start(&(dma_iter)->base, sglist, dma_nents, \ | ||
421 | pgoffset); \ | ||
422 | __sg_page_iter_dma_next(dma_iter);) | ||
423 | |||
393 | /* | 424 | /* |
394 | * Mapping sg iterator | 425 | * Mapping sg iterator |
395 | * | 426 | * |