aboutsummaryrefslogtreecommitdiffstats
path: root/net/sunrpc/xdr.c
diff options
context:
space:
mode:
Diffstat (limited to 'net/sunrpc/xdr.c')
-rw-r--r--net/sunrpc/xdr.c81
1 files changed, 52 insertions, 29 deletions
diff --git a/net/sunrpc/xdr.c b/net/sunrpc/xdr.c
index ca4bfa57e116..9022eb8b37ed 100644
--- a/net/sunrpc/xdr.c
+++ b/net/sunrpc/xdr.c
@@ -18,8 +18,8 @@
18/* 18/*
19 * XDR functions for basic NFS types 19 * XDR functions for basic NFS types
20 */ 20 */
21u32 * 21__be32 *
22xdr_encode_netobj(u32 *p, const struct xdr_netobj *obj) 22xdr_encode_netobj(__be32 *p, const struct xdr_netobj *obj)
23{ 23{
24 unsigned int quadlen = XDR_QUADLEN(obj->len); 24 unsigned int quadlen = XDR_QUADLEN(obj->len);
25 25
@@ -29,8 +29,8 @@ xdr_encode_netobj(u32 *p, const struct xdr_netobj *obj)
29 return p + XDR_QUADLEN(obj->len); 29 return p + XDR_QUADLEN(obj->len);
30} 30}
31 31
32u32 * 32__be32 *
33xdr_decode_netobj(u32 *p, struct xdr_netobj *obj) 33xdr_decode_netobj(__be32 *p, struct xdr_netobj *obj)
34{ 34{
35 unsigned int len; 35 unsigned int len;
36 36
@@ -55,7 +55,7 @@ xdr_decode_netobj(u32 *p, struct xdr_netobj *obj)
55 * Returns the updated current XDR buffer position 55 * Returns the updated current XDR buffer position
56 * 56 *
57 */ 57 */
58u32 *xdr_encode_opaque_fixed(u32 *p, const void *ptr, unsigned int nbytes) 58__be32 *xdr_encode_opaque_fixed(__be32 *p, const void *ptr, unsigned int nbytes)
59{ 59{
60 if (likely(nbytes != 0)) { 60 if (likely(nbytes != 0)) {
61 unsigned int quadlen = XDR_QUADLEN(nbytes); 61 unsigned int quadlen = XDR_QUADLEN(nbytes);
@@ -79,21 +79,21 @@ EXPORT_SYMBOL(xdr_encode_opaque_fixed);
79 * 79 *
80 * Returns the updated current XDR buffer position 80 * Returns the updated current XDR buffer position
81 */ 81 */
82u32 *xdr_encode_opaque(u32 *p, const void *ptr, unsigned int nbytes) 82__be32 *xdr_encode_opaque(__be32 *p, const void *ptr, unsigned int nbytes)
83{ 83{
84 *p++ = htonl(nbytes); 84 *p++ = htonl(nbytes);
85 return xdr_encode_opaque_fixed(p, ptr, nbytes); 85 return xdr_encode_opaque_fixed(p, ptr, nbytes);
86} 86}
87EXPORT_SYMBOL(xdr_encode_opaque); 87EXPORT_SYMBOL(xdr_encode_opaque);
88 88
89u32 * 89__be32 *
90xdr_encode_string(u32 *p, const char *string) 90xdr_encode_string(__be32 *p, const char *string)
91{ 91{
92 return xdr_encode_array(p, string, strlen(string)); 92 return xdr_encode_array(p, string, strlen(string));
93} 93}
94 94
95u32 * 95__be32 *
96xdr_decode_string_inplace(u32 *p, char **sp, int *lenp, int maxlen) 96xdr_decode_string_inplace(__be32 *p, char **sp, int *lenp, int maxlen)
97{ 97{
98 unsigned int len; 98 unsigned int len;
99 99
@@ -191,7 +191,6 @@ _shift_data_right_pages(struct page **pages, size_t pgto_base,
191 do { 191 do {
192 /* Are any pointers crossing a page boundary? */ 192 /* Are any pointers crossing a page boundary? */
193 if (pgto_base == 0) { 193 if (pgto_base == 0) {
194 flush_dcache_page(*pgto);
195 pgto_base = PAGE_CACHE_SIZE; 194 pgto_base = PAGE_CACHE_SIZE;
196 pgto--; 195 pgto--;
197 } 196 }
@@ -211,11 +210,11 @@ _shift_data_right_pages(struct page **pages, size_t pgto_base,
211 vto = kmap_atomic(*pgto, KM_USER0); 210 vto = kmap_atomic(*pgto, KM_USER0);
212 vfrom = kmap_atomic(*pgfrom, KM_USER1); 211 vfrom = kmap_atomic(*pgfrom, KM_USER1);
213 memmove(vto + pgto_base, vfrom + pgfrom_base, copy); 212 memmove(vto + pgto_base, vfrom + pgfrom_base, copy);
213 flush_dcache_page(*pgto);
214 kunmap_atomic(vfrom, KM_USER1); 214 kunmap_atomic(vfrom, KM_USER1);
215 kunmap_atomic(vto, KM_USER0); 215 kunmap_atomic(vto, KM_USER0);
216 216
217 } while ((len -= copy) != 0); 217 } while ((len -= copy) != 0);
218 flush_dcache_page(*pgto);
219} 218}
220 219
221/* 220/*
@@ -433,7 +432,7 @@ xdr_shift_buf(struct xdr_buf *buf, size_t len)
433 * of the buffer length, and takes care of adjusting the kvec 432 * of the buffer length, and takes care of adjusting the kvec
434 * length for us. 433 * length for us.
435 */ 434 */
436void xdr_init_encode(struct xdr_stream *xdr, struct xdr_buf *buf, uint32_t *p) 435void xdr_init_encode(struct xdr_stream *xdr, struct xdr_buf *buf, __be32 *p)
437{ 436{
438 struct kvec *iov = buf->head; 437 struct kvec *iov = buf->head;
439 int scratch_len = buf->buflen - buf->page_len - buf->tail[0].iov_len; 438 int scratch_len = buf->buflen - buf->page_len - buf->tail[0].iov_len;
@@ -441,8 +440,8 @@ void xdr_init_encode(struct xdr_stream *xdr, struct xdr_buf *buf, uint32_t *p)
441 BUG_ON(scratch_len < 0); 440 BUG_ON(scratch_len < 0);
442 xdr->buf = buf; 441 xdr->buf = buf;
443 xdr->iov = iov; 442 xdr->iov = iov;
444 xdr->p = (uint32_t *)((char *)iov->iov_base + iov->iov_len); 443 xdr->p = (__be32 *)((char *)iov->iov_base + iov->iov_len);
445 xdr->end = (uint32_t *)((char *)iov->iov_base + scratch_len); 444 xdr->end = (__be32 *)((char *)iov->iov_base + scratch_len);
446 BUG_ON(iov->iov_len > scratch_len); 445 BUG_ON(iov->iov_len > scratch_len);
447 446
448 if (p != xdr->p && p != NULL) { 447 if (p != xdr->p && p != NULL) {
@@ -466,10 +465,10 @@ EXPORT_SYMBOL(xdr_init_encode);
466 * bytes of data. If so, update the total xdr_buf length, and 465 * bytes of data. If so, update the total xdr_buf length, and
467 * adjust the length of the current kvec. 466 * adjust the length of the current kvec.
468 */ 467 */
469uint32_t * xdr_reserve_space(struct xdr_stream *xdr, size_t nbytes) 468__be32 * xdr_reserve_space(struct xdr_stream *xdr, size_t nbytes)
470{ 469{
471 uint32_t *p = xdr->p; 470 __be32 *p = xdr->p;
472 uint32_t *q; 471 __be32 *q;
473 472
474 /* align nbytes on the next 32-bit boundary */ 473 /* align nbytes on the next 32-bit boundary */
475 nbytes += 3; 474 nbytes += 3;
@@ -525,7 +524,7 @@ EXPORT_SYMBOL(xdr_write_pages);
525 * @buf: pointer to XDR buffer from which to decode data 524 * @buf: pointer to XDR buffer from which to decode data
526 * @p: current pointer inside XDR buffer 525 * @p: current pointer inside XDR buffer
527 */ 526 */
528void xdr_init_decode(struct xdr_stream *xdr, struct xdr_buf *buf, uint32_t *p) 527void xdr_init_decode(struct xdr_stream *xdr, struct xdr_buf *buf, __be32 *p)
529{ 528{
530 struct kvec *iov = buf->head; 529 struct kvec *iov = buf->head;
531 unsigned int len = iov->iov_len; 530 unsigned int len = iov->iov_len;
@@ -535,7 +534,7 @@ void xdr_init_decode(struct xdr_stream *xdr, struct xdr_buf *buf, uint32_t *p)
535 xdr->buf = buf; 534 xdr->buf = buf;
536 xdr->iov = iov; 535 xdr->iov = iov;
537 xdr->p = p; 536 xdr->p = p;
538 xdr->end = (uint32_t *)((char *)iov->iov_base + len); 537 xdr->end = (__be32 *)((char *)iov->iov_base + len);
539} 538}
540EXPORT_SYMBOL(xdr_init_decode); 539EXPORT_SYMBOL(xdr_init_decode);
541 540
@@ -549,10 +548,10 @@ EXPORT_SYMBOL(xdr_init_decode);
549 * If so return the current pointer, then update the current 548 * If so return the current pointer, then update the current
550 * pointer position. 549 * pointer position.
551 */ 550 */
552uint32_t * xdr_inline_decode(struct xdr_stream *xdr, size_t nbytes) 551__be32 * xdr_inline_decode(struct xdr_stream *xdr, size_t nbytes)
553{ 552{
554 uint32_t *p = xdr->p; 553 __be32 *p = xdr->p;
555 uint32_t *q = p + XDR_QUADLEN(nbytes); 554 __be32 *q = p + XDR_QUADLEN(nbytes);
556 555
557 if (unlikely(q > xdr->end || q < p)) 556 if (unlikely(q > xdr->end || q < p))
558 return NULL; 557 return NULL;
@@ -568,8 +567,7 @@ EXPORT_SYMBOL(xdr_inline_decode);
568 * 567 *
569 * Moves data beyond the current pointer position from the XDR head[] buffer 568 * Moves data beyond the current pointer position from the XDR head[] buffer
570 * into the page list. Any data that lies beyond current position + "len" 569 * into the page list. Any data that lies beyond current position + "len"
571 * bytes is moved into the XDR tail[]. The current pointer is then 570 * bytes is moved into the XDR tail[].
572 * repositioned at the beginning of the XDR tail.
573 */ 571 */
574void xdr_read_pages(struct xdr_stream *xdr, unsigned int len) 572void xdr_read_pages(struct xdr_stream *xdr, unsigned int len)
575{ 573{
@@ -601,11 +599,36 @@ void xdr_read_pages(struct xdr_stream *xdr, unsigned int len)
601 * Position current pointer at beginning of tail, and 599 * Position current pointer at beginning of tail, and
602 * set remaining message length. 600 * set remaining message length.
603 */ 601 */
604 xdr->p = (uint32_t *)((char *)iov->iov_base + padding); 602 xdr->p = (__be32 *)((char *)iov->iov_base + padding);
605 xdr->end = (uint32_t *)((char *)iov->iov_base + end); 603 xdr->end = (__be32 *)((char *)iov->iov_base + end);
606} 604}
607EXPORT_SYMBOL(xdr_read_pages); 605EXPORT_SYMBOL(xdr_read_pages);
608 606
607/**
608 * xdr_enter_page - decode data from the XDR page
609 * @xdr: pointer to xdr_stream struct
610 * @len: number of bytes of page data
611 *
612 * Moves data beyond the current pointer position from the XDR head[] buffer
613 * into the page list. Any data that lies beyond current position + "len"
614 * bytes is moved into the XDR tail[]. The current pointer is then
615 * repositioned at the beginning of the first XDR page.
616 */
617void xdr_enter_page(struct xdr_stream *xdr, unsigned int len)
618{
619 char * kaddr = page_address(xdr->buf->pages[0]);
620 xdr_read_pages(xdr, len);
621 /*
622 * Position current pointer at beginning of tail, and
623 * set remaining message length.
624 */
625 if (len > PAGE_CACHE_SIZE - xdr->buf->page_base)
626 len = PAGE_CACHE_SIZE - xdr->buf->page_base;
627 xdr->p = (__be32 *)(kaddr + xdr->buf->page_base);
628 xdr->end = (__be32 *)((char *)xdr->p + len);
629}
630EXPORT_SYMBOL(xdr_enter_page);
631
609static struct kvec empty_iov = {.iov_base = NULL, .iov_len = 0}; 632static struct kvec empty_iov = {.iov_base = NULL, .iov_len = 0};
610 633
611void 634void
@@ -720,7 +743,7 @@ out:
720int 743int
721xdr_decode_word(struct xdr_buf *buf, int base, u32 *obj) 744xdr_decode_word(struct xdr_buf *buf, int base, u32 *obj)
722{ 745{
723 u32 raw; 746 __be32 raw;
724 int status; 747 int status;
725 748
726 status = read_bytes_from_xdr_buf(buf, base, &raw, sizeof(*obj)); 749 status = read_bytes_from_xdr_buf(buf, base, &raw, sizeof(*obj));
@@ -733,7 +756,7 @@ xdr_decode_word(struct xdr_buf *buf, int base, u32 *obj)
733int 756int
734xdr_encode_word(struct xdr_buf *buf, int base, u32 obj) 757xdr_encode_word(struct xdr_buf *buf, int base, u32 obj)
735{ 758{
736 u32 raw = htonl(obj); 759 __be32 raw = htonl(obj);
737 760
738 return write_bytes_to_xdr_buf(buf, base, &raw, sizeof(obj)); 761 return write_bytes_to_xdr_buf(buf, base, &raw, sizeof(obj));
739} 762}