Skip to content

Commit

Permalink
Merge git://git.samba.org/sfrench/cifs-2.6
Browse files Browse the repository at this point in the history
* git://git.samba.org/sfrench/cifs-2.6:
  CIFS: Rename *UCS* functions to *UTF16*
  [CIFS] ACL and FSCACHE support no longer EXPERIMENTAL
  [CIFS] Fix build break with multiuser patch when LANMAN disabled
  cifs: warn about impending deprecation of legacy MultiuserMount code
  cifs: fetch credentials out of keyring for non-krb5 auth multiuser mounts
  cifs: sanitize username handling
  keys: add a "logon" key type
  cifs: lower default wsize when unix extensions are not used
  cifs: better instrumentation for coalesce_t2
  cifs: integer overflow in parse_dacl()
  cifs: Fix sparse warning when calling cifs_strtoUCS
  CIFS: Add descriptions to the brlock cache functions
  • Loading branch information
torvalds committed Jan 23, 2012
2 parents dcd6c92 + acbbb76 commit 7908b3e
Show file tree
Hide file tree
Showing 17 changed files with 462 additions and 202 deletions.
3 changes: 1 addition & 2 deletions fs/cifs/Kconfig
Expand Up @@ -140,7 +140,6 @@ config CIFS_DFS_UPCALL


config CIFS_FSCACHE config CIFS_FSCACHE
bool "Provide CIFS client caching support (EXPERIMENTAL)" bool "Provide CIFS client caching support (EXPERIMENTAL)"
depends on EXPERIMENTAL
depends on CIFS=m && FSCACHE || CIFS=y && FSCACHE=y depends on CIFS=m && FSCACHE || CIFS=y && FSCACHE=y
help help
Makes CIFS FS-Cache capable. Say Y here if you want your CIFS data Makes CIFS FS-Cache capable. Say Y here if you want your CIFS data
Expand All @@ -149,7 +148,7 @@ config CIFS_FSCACHE


config CIFS_ACL config CIFS_ACL
bool "Provide CIFS ACL support (EXPERIMENTAL)" bool "Provide CIFS ACL support (EXPERIMENTAL)"
depends on EXPERIMENTAL && CIFS_XATTR && KEYS depends on CIFS_XATTR && KEYS
help help
Allows to fetch CIFS/NTFS ACL from the server. The DACL blob Allows to fetch CIFS/NTFS ACL from the server. The DACL blob
is handed over to the application/caller. is handed over to the application/caller.
Expand Down
11 changes: 10 additions & 1 deletion fs/cifs/cifs_debug.c
Expand Up @@ -676,14 +676,23 @@ static ssize_t cifs_multiuser_mount_proc_write(struct file *file,
{ {
char c; char c;
int rc; int rc;
static bool warned;


rc = get_user(c, buffer); rc = get_user(c, buffer);
if (rc) if (rc)
return rc; return rc;
if (c == '0' || c == 'n' || c == 'N') if (c == '0' || c == 'n' || c == 'N')
multiuser_mount = 0; multiuser_mount = 0;
else if (c == '1' || c == 'y' || c == 'Y') else if (c == '1' || c == 'y' || c == 'Y') {
multiuser_mount = 1; multiuser_mount = 1;
if (!warned) {
warned = true;
printk(KERN_WARNING "CIFS VFS: The legacy multiuser "
"mount code is scheduled to be deprecated in "
"3.5. Please switch to using the multiuser "
"mount option.");
}
}


return count; return count;
} }
Expand Down
10 changes: 7 additions & 3 deletions fs/cifs/cifs_spnego.c
Expand Up @@ -113,9 +113,11 @@ cifs_get_spnego_key(struct cifs_ses *sesInfo)
MAX_MECH_STR_LEN + MAX_MECH_STR_LEN +
UID_KEY_LEN + (sizeof(uid_t) * 2) + UID_KEY_LEN + (sizeof(uid_t) * 2) +
CREDUID_KEY_LEN + (sizeof(uid_t) * 2) + CREDUID_KEY_LEN + (sizeof(uid_t) * 2) +
USER_KEY_LEN + strlen(sesInfo->user_name) +
PID_KEY_LEN + (sizeof(pid_t) * 2) + 1; PID_KEY_LEN + (sizeof(pid_t) * 2) + 1;


if (sesInfo->user_name)
desc_len += USER_KEY_LEN + strlen(sesInfo->user_name);

spnego_key = ERR_PTR(-ENOMEM); spnego_key = ERR_PTR(-ENOMEM);
description = kzalloc(desc_len, GFP_KERNEL); description = kzalloc(desc_len, GFP_KERNEL);
if (description == NULL) if (description == NULL)
Expand Down Expand Up @@ -152,8 +154,10 @@ cifs_get_spnego_key(struct cifs_ses *sesInfo)
dp = description + strlen(description); dp = description + strlen(description);
sprintf(dp, ";creduid=0x%x", sesInfo->cred_uid); sprintf(dp, ";creduid=0x%x", sesInfo->cred_uid);


dp = description + strlen(description); if (sesInfo->user_name) {
sprintf(dp, ";user=%s", sesInfo->user_name); dp = description + strlen(description);
sprintf(dp, ";user=%s", sesInfo->user_name);
}


dp = description + strlen(description); dp = description + strlen(description);
sprintf(dp, ";pid=0x%x", current->pid); sprintf(dp, ";pid=0x%x", current->pid);
Expand Down
41 changes: 21 additions & 20 deletions fs/cifs/cifs_unicode.c
Expand Up @@ -27,17 +27,17 @@
#include "cifs_debug.h" #include "cifs_debug.h"


/* /*
* cifs_ucs2_bytes - how long will a string be after conversion? * cifs_utf16_bytes - how long will a string be after conversion?
* @ucs - pointer to input string * @utf16 - pointer to input string
* @maxbytes - don't go past this many bytes of input string * @maxbytes - don't go past this many bytes of input string
* @codepage - destination codepage * @codepage - destination codepage
* *
* Walk a ucs2le string and return the number of bytes that the string will * Walk a utf16le string and return the number of bytes that the string will
* be after being converted to the given charset, not including any null * be after being converted to the given charset, not including any null
* termination required. Don't walk past maxbytes in the source buffer. * termination required. Don't walk past maxbytes in the source buffer.
*/ */
int int
cifs_ucs2_bytes(const __le16 *from, int maxbytes, cifs_utf16_bytes(const __le16 *from, int maxbytes,
const struct nls_table *codepage) const struct nls_table *codepage)
{ {
int i; int i;
Expand Down Expand Up @@ -122,15 +122,15 @@ cifs_mapchar(char *target, const __u16 src_char, const struct nls_table *cp,
} }


/* /*
* cifs_from_ucs2 - convert utf16le string to local charset * cifs_from_utf16 - convert utf16le string to local charset
* @to - destination buffer * @to - destination buffer
* @from - source buffer * @from - source buffer
* @tolen - destination buffer size (in bytes) * @tolen - destination buffer size (in bytes)
* @fromlen - source buffer size (in bytes) * @fromlen - source buffer size (in bytes)
* @codepage - codepage to which characters should be converted * @codepage - codepage to which characters should be converted
* @mapchar - should characters be remapped according to the mapchars option? * @mapchar - should characters be remapped according to the mapchars option?
* *
* Convert a little-endian ucs2le string (as sent by the server) to a string * Convert a little-endian utf16le string (as sent by the server) to a string
* in the provided codepage. The tolen and fromlen parameters are to ensure * in the provided codepage. The tolen and fromlen parameters are to ensure
* that the code doesn't walk off of the end of the buffer (which is always * that the code doesn't walk off of the end of the buffer (which is always
* a danger if the alignment of the source buffer is off). The destination * a danger if the alignment of the source buffer is off). The destination
Expand All @@ -139,12 +139,12 @@ cifs_mapchar(char *target, const __u16 src_char, const struct nls_table *cp,
* null terminator). * null terminator).
* *
* Note that some windows versions actually send multiword UTF-16 characters * Note that some windows versions actually send multiword UTF-16 characters
* instead of straight UCS-2. The linux nls routines however aren't able to * instead of straight UTF16-2. The linux nls routines however aren't able to
* deal with those characters properly. In the event that we get some of * deal with those characters properly. In the event that we get some of
* those characters, they won't be translated properly. * those characters, they won't be translated properly.
*/ */
int int
cifs_from_ucs2(char *to, const __le16 *from, int tolen, int fromlen, cifs_from_utf16(char *to, const __le16 *from, int tolen, int fromlen,
const struct nls_table *codepage, bool mapchar) const struct nls_table *codepage, bool mapchar)
{ {
int i, charlen, safelen; int i, charlen, safelen;
Expand Down Expand Up @@ -190,13 +190,13 @@ cifs_from_ucs2(char *to, const __le16 *from, int tolen, int fromlen,
} }


/* /*
* NAME: cifs_strtoUCS() * NAME: cifs_strtoUTF16()
* *
* FUNCTION: Convert character string to unicode string * FUNCTION: Convert character string to unicode string
* *
*/ */
int int
cifs_strtoUCS(__le16 *to, const char *from, int len, cifs_strtoUTF16(__le16 *to, const char *from, int len,
const struct nls_table *codepage) const struct nls_table *codepage)
{ {
int charlen; int charlen;
Expand All @@ -206,7 +206,7 @@ cifs_strtoUCS(__le16 *to, const char *from, int len,
for (i = 0; len && *from; i++, from += charlen, len -= charlen) { for (i = 0; len && *from; i++, from += charlen, len -= charlen) {
charlen = codepage->char2uni(from, len, &wchar_to); charlen = codepage->char2uni(from, len, &wchar_to);
if (charlen < 1) { if (charlen < 1) {
cERROR(1, "strtoUCS: char2uni of 0x%x returned %d", cERROR(1, "strtoUTF16: char2uni of 0x%x returned %d",
*from, charlen); *from, charlen);
/* A question mark */ /* A question mark */
wchar_to = 0x003f; wchar_to = 0x003f;
Expand All @@ -220,7 +220,8 @@ cifs_strtoUCS(__le16 *to, const char *from, int len,
} }


/* /*
* cifs_strndup_from_ucs - copy a string from wire format to the local codepage * cifs_strndup_from_utf16 - copy a string from wire format to the local
* codepage
* @src - source string * @src - source string
* @maxlen - don't walk past this many bytes in the source string * @maxlen - don't walk past this many bytes in the source string
* @is_unicode - is this a unicode string? * @is_unicode - is this a unicode string?
Expand All @@ -231,19 +232,19 @@ cifs_strtoUCS(__le16 *to, const char *from, int len,
* error. * error.
*/ */
char * char *
cifs_strndup_from_ucs(const char *src, const int maxlen, const bool is_unicode, cifs_strndup_from_utf16(const char *src, const int maxlen,
const struct nls_table *codepage) const bool is_unicode, const struct nls_table *codepage)
{ {
int len; int len;
char *dst; char *dst;


if (is_unicode) { if (is_unicode) {
len = cifs_ucs2_bytes((__le16 *) src, maxlen, codepage); len = cifs_utf16_bytes((__le16 *) src, maxlen, codepage);
len += nls_nullsize(codepage); len += nls_nullsize(codepage);
dst = kmalloc(len, GFP_KERNEL); dst = kmalloc(len, GFP_KERNEL);
if (!dst) if (!dst)
return NULL; return NULL;
cifs_from_ucs2(dst, (__le16 *) src, len, maxlen, codepage, cifs_from_utf16(dst, (__le16 *) src, len, maxlen, codepage,
false); false);
} else { } else {
len = strnlen(src, maxlen); len = strnlen(src, maxlen);
Expand All @@ -264,7 +265,7 @@ cifs_strndup_from_ucs(const char *src, const int maxlen, const bool is_unicode,
* names are little endian 16 bit Unicode on the wire * names are little endian 16 bit Unicode on the wire
*/ */
int int
cifsConvertToUCS(__le16 *target, const char *source, int srclen, cifsConvertToUTF16(__le16 *target, const char *source, int srclen,
const struct nls_table *cp, int mapChars) const struct nls_table *cp, int mapChars)
{ {
int i, j, charlen; int i, j, charlen;
Expand All @@ -273,15 +274,15 @@ cifsConvertToUCS(__le16 *target, const char *source, int srclen,
wchar_t tmp; wchar_t tmp;


if (!mapChars) if (!mapChars)
return cifs_strtoUCS(target, source, PATH_MAX, cp); return cifs_strtoUTF16(target, source, PATH_MAX, cp);


for (i = 0, j = 0; i < srclen; j++) { for (i = 0, j = 0; i < srclen; j++) {
src_char = source[i]; src_char = source[i];
charlen = 1; charlen = 1;
switch (src_char) { switch (src_char) {
case 0: case 0:
put_unaligned(0, &target[j]); put_unaligned(0, &target[j]);
goto ctoUCS_out; goto ctoUTF16_out;
case ':': case ':':
dst_char = cpu_to_le16(UNI_COLON); dst_char = cpu_to_le16(UNI_COLON);
break; break;
Expand Down Expand Up @@ -326,7 +327,7 @@ cifsConvertToUCS(__le16 *target, const char *source, int srclen,
put_unaligned(dst_char, &target[j]); put_unaligned(dst_char, &target[j]);
} }


ctoUCS_out: ctoUTF16_out:
return i; return i;
} }


20 changes: 10 additions & 10 deletions fs/cifs/cifs_unicode.h
Expand Up @@ -74,16 +74,16 @@ extern const struct UniCaseRange CifsUniLowerRange[];
#endif /* UNIUPR_NOLOWER */ #endif /* UNIUPR_NOLOWER */


#ifdef __KERNEL__ #ifdef __KERNEL__
int cifs_from_ucs2(char *to, const __le16 *from, int tolen, int fromlen, int cifs_from_utf16(char *to, const __le16 *from, int tolen, int fromlen,
const struct nls_table *codepage, bool mapchar); const struct nls_table *codepage, bool mapchar);
int cifs_ucs2_bytes(const __le16 *from, int maxbytes, int cifs_utf16_bytes(const __le16 *from, int maxbytes,
const struct nls_table *codepage); const struct nls_table *codepage);
int cifs_strtoUCS(__le16 *, const char *, int, const struct nls_table *); int cifs_strtoUTF16(__le16 *, const char *, int, const struct nls_table *);
char *cifs_strndup_from_ucs(const char *src, const int maxlen, char *cifs_strndup_from_utf16(const char *src, const int maxlen,
const bool is_unicode, const bool is_unicode,
const struct nls_table *codepage); const struct nls_table *codepage);
extern int cifsConvertToUCS(__le16 *target, const char *source, int maxlen, extern int cifsConvertToUTF16(__le16 *target, const char *source, int maxlen,
const struct nls_table *cp, int mapChars); const struct nls_table *cp, int mapChars);


#endif #endif


Expand Down
2 changes: 2 additions & 0 deletions fs/cifs/cifsacl.c
Expand Up @@ -909,6 +909,8 @@ static void parse_dacl(struct cifs_acl *pdacl, char *end_of_acl,
umode_t group_mask = S_IRWXG; umode_t group_mask = S_IRWXG;
umode_t other_mask = S_IRWXU | S_IRWXG | S_IRWXO; umode_t other_mask = S_IRWXU | S_IRWXG | S_IRWXO;


if (num_aces > ULONG_MAX / sizeof(struct cifs_ace *))
return;
ppace = kmalloc(num_aces * sizeof(struct cifs_ace *), ppace = kmalloc(num_aces * sizeof(struct cifs_ace *),
GFP_KERNEL); GFP_KERNEL);
if (!ppace) { if (!ppace) {
Expand Down
21 changes: 13 additions & 8 deletions fs/cifs/cifsencrypt.c
Expand Up @@ -327,7 +327,7 @@ build_avpair_blob(struct cifs_ses *ses, const struct nls_table *nls_cp)
attrptr->type = cpu_to_le16(NTLMSSP_AV_NB_DOMAIN_NAME); attrptr->type = cpu_to_le16(NTLMSSP_AV_NB_DOMAIN_NAME);
attrptr->length = cpu_to_le16(2 * dlen); attrptr->length = cpu_to_le16(2 * dlen);
blobptr = (unsigned char *)attrptr + sizeof(struct ntlmssp2_name); blobptr = (unsigned char *)attrptr + sizeof(struct ntlmssp2_name);
cifs_strtoUCS((__le16 *)blobptr, ses->domainName, dlen, nls_cp); cifs_strtoUTF16((__le16 *)blobptr, ses->domainName, dlen, nls_cp);


return 0; return 0;
} }
Expand Down Expand Up @@ -376,7 +376,7 @@ find_domain_name(struct cifs_ses *ses, const struct nls_table *nls_cp)
kmalloc(attrsize + 1, GFP_KERNEL); kmalloc(attrsize + 1, GFP_KERNEL);
if (!ses->domainName) if (!ses->domainName)
return -ENOMEM; return -ENOMEM;
cifs_from_ucs2(ses->domainName, cifs_from_utf16(ses->domainName,
(__le16 *)blobptr, attrsize, attrsize, (__le16 *)blobptr, attrsize, attrsize,
nls_cp, false); nls_cp, false);
break; break;
Expand Down Expand Up @@ -420,15 +420,20 @@ static int calc_ntlmv2_hash(struct cifs_ses *ses, char *ntlmv2_hash,
} }


/* convert ses->user_name to unicode and uppercase */ /* convert ses->user_name to unicode and uppercase */
len = strlen(ses->user_name); len = ses->user_name ? strlen(ses->user_name) : 0;
user = kmalloc(2 + (len * 2), GFP_KERNEL); user = kmalloc(2 + (len * 2), GFP_KERNEL);
if (user == NULL) { if (user == NULL) {
cERROR(1, "calc_ntlmv2_hash: user mem alloc failure\n"); cERROR(1, "calc_ntlmv2_hash: user mem alloc failure\n");
rc = -ENOMEM; rc = -ENOMEM;
return rc; return rc;
} }
len = cifs_strtoUCS((__le16 *)user, ses->user_name, len, nls_cp);
UniStrupr(user); if (len) {
len = cifs_strtoUTF16((__le16 *)user, ses->user_name, len, nls_cp);
UniStrupr(user);
} else {
memset(user, '\0', 2);
}


rc = crypto_shash_update(&ses->server->secmech.sdeschmacmd5->shash, rc = crypto_shash_update(&ses->server->secmech.sdeschmacmd5->shash,
(char *)user, 2 * len); (char *)user, 2 * len);
Expand All @@ -448,8 +453,8 @@ static int calc_ntlmv2_hash(struct cifs_ses *ses, char *ntlmv2_hash,
rc = -ENOMEM; rc = -ENOMEM;
return rc; return rc;
} }
len = cifs_strtoUCS((__le16 *)domain, ses->domainName, len, len = cifs_strtoUTF16((__le16 *)domain, ses->domainName, len,
nls_cp); nls_cp);
rc = rc =
crypto_shash_update(&ses->server->secmech.sdeschmacmd5->shash, crypto_shash_update(&ses->server->secmech.sdeschmacmd5->shash,
(char *)domain, 2 * len); (char *)domain, 2 * len);
Expand All @@ -468,7 +473,7 @@ static int calc_ntlmv2_hash(struct cifs_ses *ses, char *ntlmv2_hash,
rc = -ENOMEM; rc = -ENOMEM;
return rc; return rc;
} }
len = cifs_strtoUCS((__le16 *)server, ses->serverName, len, len = cifs_strtoUTF16((__le16 *)server, ses->serverName, len,
nls_cp); nls_cp);
rc = rc =
crypto_shash_update(&ses->server->secmech.sdeschmacmd5->shash, crypto_shash_update(&ses->server->secmech.sdeschmacmd5->shash,
Expand Down
2 changes: 2 additions & 0 deletions fs/cifs/cifsglob.h
Expand Up @@ -879,6 +879,8 @@ require use of the stronger protocol */
#define CIFSSEC_MASK 0xB70B7 /* current flags supported if weak */ #define CIFSSEC_MASK 0xB70B7 /* current flags supported if weak */
#endif /* UPCALL */ #endif /* UPCALL */
#else /* do not allow weak pw hash */ #else /* do not allow weak pw hash */
#define CIFSSEC_MUST_LANMAN 0
#define CIFSSEC_MUST_PLNTXT 0
#ifdef CONFIG_CIFS_UPCALL #ifdef CONFIG_CIFS_UPCALL
#define CIFSSEC_MASK 0x8F08F /* flags supported if no weak allowed */ #define CIFSSEC_MASK 0x8F08F /* flags supported if no weak allowed */
#else #else
Expand Down

0 comments on commit 7908b3e

Please sign in to comment.