diff options
author | Weston Andros Adamson <dros@netapp.com> | 2012-04-24 11:07:59 -0400 |
---|---|---|
committer | J. Bruce Fields <bfields@redhat.com> | 2012-05-31 20:29:38 -0400 |
commit | e7a0444aef4a1649bc155fd5c6d6ab3f8bdc88ab (patch) | |
tree | e3afdeb61ecb045dd95c371f4d6cc89246d0663b /fs/nfsd | |
parent | 45eaa1c1a16122a98bf995c004c23806759d2e5f (diff) |
nfsd: add IPv6 addr escaping to fs_location hosts
The fs_location->hosts list is split on colons, but this doesn't work when
IPv6 addresses are used (they contain colons).
This patch adds the function nfsd4_encode_components_esc() to
allow the caller to specify escape characters when splitting on 'sep'.
In order to fix referrals, this patch must be used with the mountd patch
that similarly fixes IPv6 [] escaping.
Signed-off-by: Weston Andros Adamson <dros@netapp.com>
Signed-off-by: J. Bruce Fields <bfields@redhat.com>
Diffstat (limited to 'fs/nfsd')
-rw-r--r-- | fs/nfsd/nfs4xdr.c | 40 |
1 files changed, 33 insertions, 7 deletions
diff --git a/fs/nfsd/nfs4xdr.c b/fs/nfsd/nfs4xdr.c index 61555e756410..30817e9f1bb7 100644 --- a/fs/nfsd/nfs4xdr.c +++ b/fs/nfsd/nfs4xdr.c | |||
@@ -1744,15 +1744,16 @@ static void encode_seqid_op_tail(struct nfsd4_compoundres *resp, __be32 *save, _ | |||
1744 | } | 1744 | } |
1745 | 1745 | ||
1746 | /* Encode as an array of strings the string given with components | 1746 | /* Encode as an array of strings the string given with components |
1747 | * separated @sep. | 1747 | * separated @sep, escaped with esc_enter and esc_exit. |
1748 | */ | 1748 | */ |
1749 | static __be32 nfsd4_encode_components(char sep, char *components, | 1749 | static __be32 nfsd4_encode_components_esc(char sep, char *components, |
1750 | __be32 **pp, int *buflen) | 1750 | __be32 **pp, int *buflen, |
1751 | char esc_enter, char esc_exit) | ||
1751 | { | 1752 | { |
1752 | __be32 *p = *pp; | 1753 | __be32 *p = *pp; |
1753 | __be32 *countp = p; | 1754 | __be32 *countp = p; |
1754 | int strlen, count=0; | 1755 | int strlen, count=0; |
1755 | char *str, *end; | 1756 | char *str, *end, *next; |
1756 | 1757 | ||
1757 | dprintk("nfsd4_encode_components(%s)\n", components); | 1758 | dprintk("nfsd4_encode_components(%s)\n", components); |
1758 | if ((*buflen -= 4) < 0) | 1759 | if ((*buflen -= 4) < 0) |
@@ -1760,8 +1761,23 @@ static __be32 nfsd4_encode_components(char sep, char *components, | |||
1760 | WRITE32(0); /* We will fill this in with @count later */ | 1761 | WRITE32(0); /* We will fill this in with @count later */ |
1761 | end = str = components; | 1762 | end = str = components; |
1762 | while (*end) { | 1763 | while (*end) { |
1763 | for (; *end && (*end != sep); end++) | 1764 | bool found_esc = false; |
1764 | ; /* Point to end of component */ | 1765 | |
1766 | /* try to parse as esc_start, ..., esc_end, sep */ | ||
1767 | if (*str == esc_enter) { | ||
1768 | for (; *end && (*end != esc_exit); end++) | ||
1769 | /* find esc_exit or end of string */; | ||
1770 | next = end + 1; | ||
1771 | if (*end && (!*next || *next == sep)) { | ||
1772 | str++; | ||
1773 | found_esc = true; | ||
1774 | } | ||
1775 | } | ||
1776 | |||
1777 | if (!found_esc) | ||
1778 | for (; *end && (*end != sep); end++) | ||
1779 | /* find sep or end of string */; | ||
1780 | |||
1765 | strlen = end - str; | 1781 | strlen = end - str; |
1766 | if (strlen) { | 1782 | if (strlen) { |
1767 | if ((*buflen -= ((XDR_QUADLEN(strlen) << 2) + 4)) < 0) | 1783 | if ((*buflen -= ((XDR_QUADLEN(strlen) << 2) + 4)) < 0) |
@@ -1780,6 +1796,15 @@ static __be32 nfsd4_encode_components(char sep, char *components, | |||
1780 | return 0; | 1796 | return 0; |
1781 | } | 1797 | } |
1782 | 1798 | ||
1799 | /* Encode as an array of strings the string given with components | ||
1800 | * separated @sep. | ||
1801 | */ | ||
1802 | static __be32 nfsd4_encode_components(char sep, char *components, | ||
1803 | __be32 **pp, int *buflen) | ||
1804 | { | ||
1805 | return nfsd4_encode_components_esc(sep, components, pp, buflen, 0, 0); | ||
1806 | } | ||
1807 | |||
1783 | /* | 1808 | /* |
1784 | * encode a location element of a fs_locations structure | 1809 | * encode a location element of a fs_locations structure |
1785 | */ | 1810 | */ |
@@ -1789,7 +1814,8 @@ static __be32 nfsd4_encode_fs_location4(struct nfsd4_fs_location *location, | |||
1789 | __be32 status; | 1814 | __be32 status; |
1790 | __be32 *p = *pp; | 1815 | __be32 *p = *pp; |
1791 | 1816 | ||
1792 | status = nfsd4_encode_components(':', location->hosts, &p, buflen); | 1817 | status = nfsd4_encode_components_esc(':', location->hosts, &p, buflen, |
1818 | '[', ']'); | ||
1793 | if (status) | 1819 | if (status) |
1794 | return status; | 1820 | return status; |
1795 | status = nfsd4_encode_components('/', location->path, &p, buflen); | 1821 | status = nfsd4_encode_components('/', location->path, &p, buflen); |