diff options
Diffstat (limited to 'crypto/scatterwalk.h')
-rw-r--r-- | crypto/scatterwalk.h | 52 |
1 files changed, 30 insertions, 22 deletions
diff --git a/crypto/scatterwalk.h b/crypto/scatterwalk.h index e79925c474a3..f1592cc2d0f4 100644 --- a/crypto/scatterwalk.h +++ b/crypto/scatterwalk.h | |||
@@ -14,45 +14,42 @@ | |||
14 | 14 | ||
15 | #ifndef _CRYPTO_SCATTERWALK_H | 15 | #ifndef _CRYPTO_SCATTERWALK_H |
16 | #define _CRYPTO_SCATTERWALK_H | 16 | #define _CRYPTO_SCATTERWALK_H |
17 | |||
17 | #include <linux/mm.h> | 18 | #include <linux/mm.h> |
18 | #include <asm/scatterlist.h> | 19 | #include <linux/scatterlist.h> |
19 | 20 | ||
20 | struct scatter_walk { | 21 | #include "internal.h" |
21 | struct scatterlist *sg; | ||
22 | struct page *page; | ||
23 | void *data; | ||
24 | unsigned int len_this_page; | ||
25 | unsigned int len_this_segment; | ||
26 | unsigned int offset; | ||
27 | }; | ||
28 | 22 | ||
29 | /* Define sg_next is an inline routine now in case we want to change | ||
30 | scatterlist to a linked list later. */ | ||
31 | static inline struct scatterlist *sg_next(struct scatterlist *sg) | 23 | static inline struct scatterlist *sg_next(struct scatterlist *sg) |
32 | { | 24 | { |
33 | return sg + 1; | 25 | return (++sg)->length ? sg : (void *)sg->page; |
34 | } | 26 | } |
35 | 27 | ||
36 | static inline int scatterwalk_samebuf(struct scatter_walk *walk_in, | 28 | static inline unsigned long scatterwalk_samebuf(struct scatter_walk *walk_in, |
37 | struct scatter_walk *walk_out) | 29 | struct scatter_walk *walk_out) |
38 | { | 30 | { |
39 | return walk_in->page == walk_out->page && | 31 | return !(((walk_in->sg->page - walk_out->sg->page) << PAGE_SHIFT) + |
40 | walk_in->offset == walk_out->offset; | 32 | (int)(walk_in->offset - walk_out->offset)); |
33 | } | ||
34 | |||
35 | static inline unsigned int scatterwalk_pagelen(struct scatter_walk *walk) | ||
36 | { | ||
37 | unsigned int len = walk->sg->offset + walk->sg->length - walk->offset; | ||
38 | unsigned int len_this_page = offset_in_page(~walk->offset) + 1; | ||
39 | return len_this_page > len ? len : len_this_page; | ||
41 | } | 40 | } |
42 | 41 | ||
43 | static inline unsigned int scatterwalk_clamp(struct scatter_walk *walk, | 42 | static inline unsigned int scatterwalk_clamp(struct scatter_walk *walk, |
44 | unsigned int nbytes) | 43 | unsigned int nbytes) |
45 | { | 44 | { |
46 | return nbytes > walk->len_this_page ? walk->len_this_page : nbytes; | 45 | unsigned int len_this_page = scatterwalk_pagelen(walk); |
46 | return nbytes > len_this_page ? len_this_page : nbytes; | ||
47 | } | 47 | } |
48 | 48 | ||
49 | static inline void scatterwalk_advance(struct scatter_walk *walk, | 49 | static inline void scatterwalk_advance(struct scatter_walk *walk, |
50 | unsigned int nbytes) | 50 | unsigned int nbytes) |
51 | { | 51 | { |
52 | walk->data += nbytes; | ||
53 | walk->offset += nbytes; | 52 | walk->offset += nbytes; |
54 | walk->len_this_page -= nbytes; | ||
55 | walk->len_this_segment -= nbytes; | ||
56 | } | 53 | } |
57 | 54 | ||
58 | static inline unsigned int scatterwalk_aligned(struct scatter_walk *walk, | 55 | static inline unsigned int scatterwalk_aligned(struct scatter_walk *walk, |
@@ -61,9 +58,20 @@ static inline unsigned int scatterwalk_aligned(struct scatter_walk *walk, | |||
61 | return !(walk->offset & alignmask); | 58 | return !(walk->offset & alignmask); |
62 | } | 59 | } |
63 | 60 | ||
61 | static inline struct page *scatterwalk_page(struct scatter_walk *walk) | ||
62 | { | ||
63 | return walk->sg->page + (walk->offset >> PAGE_SHIFT); | ||
64 | } | ||
65 | |||
66 | static inline void scatterwalk_unmap(void *vaddr, int out) | ||
67 | { | ||
68 | crypto_kunmap(vaddr, out); | ||
69 | } | ||
70 | |||
64 | void scatterwalk_start(struct scatter_walk *walk, struct scatterlist *sg); | 71 | void scatterwalk_start(struct scatter_walk *walk, struct scatterlist *sg); |
65 | int scatterwalk_copychunks(void *buf, struct scatter_walk *walk, size_t nbytes, int out); | 72 | void scatterwalk_copychunks(void *buf, struct scatter_walk *walk, |
66 | void scatterwalk_map(struct scatter_walk *walk, int out); | 73 | size_t nbytes, int out); |
74 | void *scatterwalk_map(struct scatter_walk *walk, int out); | ||
67 | void scatterwalk_done(struct scatter_walk *walk, int out, int more); | 75 | void scatterwalk_done(struct scatter_walk *walk, int out, int more); |
68 | 76 | ||
69 | #endif /* _CRYPTO_SCATTERWALK_H */ | 77 | #endif /* _CRYPTO_SCATTERWALK_H */ |