diff options
-rw-r--r-- | fs/cifs/cifs_dfs_ref.c | 14 | ||||
-rw-r--r-- | fs/cifs/cifsglob.h | 41 | ||||
-rw-r--r-- | fs/cifs/cifsproto.h | 4 | ||||
-rw-r--r-- | fs/cifs/connect.c | 12 | ||||
-rw-r--r-- | fs/cifs/dns_resolve.c | 5 | ||||
-rw-r--r-- | fs/cifs/link.c | 16 |
6 files changed, 61 insertions, 31 deletions
diff --git a/fs/cifs/cifs_dfs_ref.c b/fs/cifs/cifs_dfs_ref.c index 15e31f8435ba..413ee2349d1a 100644 --- a/fs/cifs/cifs_dfs_ref.c +++ b/fs/cifs/cifs_dfs_ref.c | |||
@@ -3,8 +3,9 @@ | |||
3 | * traversal via DFS junction point | 3 | * traversal via DFS junction point |
4 | * | 4 | * |
5 | * Copyright (c) 2007 Igor Mammedov | 5 | * Copyright (c) 2007 Igor Mammedov |
6 | * Copyright (C) International Business Machines Corp., 2008 | ||
6 | * Author(s): Igor Mammedov (niallain@gmail.com) | 7 | * Author(s): Igor Mammedov (niallain@gmail.com) |
7 | * | 8 | * Steve French (sfrench@us.ibm.com) |
8 | * This program is free software; you can redistribute it and/or | 9 | * This program is free software; you can redistribute it and/or |
9 | * modify it under the terms of the GNU General Public License | 10 | * modify it under the terms of the GNU General Public License |
10 | * as published by the Free Software Foundation; either version | 11 | * as published by the Free Software Foundation; either version |
@@ -107,8 +108,9 @@ static char *cifs_get_share_name(const char *node_name) | |||
107 | * Returns: pointer to new mount options or ERR_PTR. | 108 | * Returns: pointer to new mount options or ERR_PTR. |
108 | * Caller is responcible for freeing retunrned value if it is not error. | 109 | * Caller is responcible for freeing retunrned value if it is not error. |
109 | */ | 110 | */ |
110 | char *compose_mount_options(const char *sb_mountdata, const char *ref_unc, | 111 | static char *compose_mount_options(const char *sb_mountdata, |
111 | char **devname) | 112 | const char *ref_unc, |
113 | char **devname) | ||
112 | { | 114 | { |
113 | int rc; | 115 | int rc; |
114 | char *mountdata; | 116 | char *mountdata; |
@@ -188,13 +190,13 @@ compose_mount_options_out: | |||
188 | } | 190 | } |
189 | 191 | ||
190 | 192 | ||
191 | struct vfsmount *cifs_dfs_do_refmount(const struct vfsmount *mnt_parent, | 193 | static struct vfsmount *cifs_dfs_do_refmount(const struct vfsmount *mnt_parent, |
192 | struct dentry *dentry, char *ref_unc) | 194 | struct dentry *dentry, char *ref_unc) |
193 | { | 195 | { |
194 | struct cifs_sb_info *cifs_sb; | 196 | struct cifs_sb_info *cifs_sb; |
195 | struct vfsmount *mnt; | 197 | struct vfsmount *mnt; |
196 | char *mountdata; | 198 | char *mountdata; |
197 | char *devname; | 199 | char *devname = NULL; |
198 | 200 | ||
199 | cifs_sb = CIFS_SB(dentry->d_inode->i_sb); | 201 | cifs_sb = CIFS_SB(dentry->d_inode->i_sb); |
200 | mountdata = compose_mount_options(cifs_sb->mountdata, | 202 | mountdata = compose_mount_options(cifs_sb->mountdata, |
@@ -278,7 +280,7 @@ static int add_mount_helper(struct vfsmount *newmnt, struct nameidata *nd, | |||
278 | return err; | 280 | return err; |
279 | } | 281 | } |
280 | 282 | ||
281 | void dump_referral(const struct dfs_info3_param *ref) | 283 | static void dump_referral(const struct dfs_info3_param *ref) |
282 | { | 284 | { |
283 | cFYI(1, ("DFS: ref path: %s", ref->path_name)); | 285 | cFYI(1, ("DFS: ref path: %s", ref->path_name)); |
284 | cFYI(1, ("DFS: node path: %s", ref->node_name)); | 286 | cFYI(1, ("DFS: node path: %s", ref->node_name)); |
diff --git a/fs/cifs/cifsglob.h b/fs/cifs/cifsglob.h index 1fde2197ad76..5d32d8ddc82e 100644 --- a/fs/cifs/cifsglob.h +++ b/fs/cifs/cifsglob.h | |||
@@ -1,7 +1,7 @@ | |||
1 | /* | 1 | /* |
2 | * fs/cifs/cifsglob.h | 2 | * fs/cifs/cifsglob.h |
3 | * | 3 | * |
4 | * Copyright (C) International Business Machines Corp., 2002,2007 | 4 | * Copyright (C) International Business Machines Corp., 2002,2008 |
5 | * Author(s): Steve French (sfrench@us.ibm.com) | 5 | * Author(s): Steve French (sfrench@us.ibm.com) |
6 | * Jeremy Allison (jra@samba.org) | 6 | * Jeremy Allison (jra@samba.org) |
7 | * | 7 | * |
@@ -70,14 +70,6 @@ | |||
70 | #endif | 70 | #endif |
71 | 71 | ||
72 | /* | 72 | /* |
73 | * This information is kept on every Server we know about. | ||
74 | * | ||
75 | * Some things to note: | ||
76 | * | ||
77 | */ | ||
78 | #define SERVER_NAME_LEN_WITH_NULL (SERVER_NAME_LENGTH + 1) | ||
79 | |||
80 | /* | ||
81 | * CIFS vfs client Status information (based on what we know.) | 73 | * CIFS vfs client Status information (based on what we know.) |
82 | */ | 74 | */ |
83 | 75 | ||
@@ -460,6 +452,37 @@ struct dir_notify_req { | |||
460 | struct file *pfile; | 452 | struct file *pfile; |
461 | }; | 453 | }; |
462 | 454 | ||
455 | struct dfs_info3_param { | ||
456 | int flags; /* DFSREF_REFERRAL_SERVER, DFSREF_STORAGE_SERVER*/ | ||
457 | int PathConsumed; | ||
458 | int server_type; | ||
459 | int ref_flag; | ||
460 | char *path_name; | ||
461 | char *node_name; | ||
462 | }; | ||
463 | |||
464 | static inline void free_dfs_info_param(struct dfs_info3_param *param) | ||
465 | { | ||
466 | if (param) { | ||
467 | kfree(param->path_name); | ||
468 | kfree(param->node_name); | ||
469 | kfree(param); | ||
470 | } | ||
471 | } | ||
472 | |||
473 | static inline void free_dfs_info_array(struct dfs_info3_param *param, | ||
474 | int number_of_items) | ||
475 | { | ||
476 | int i; | ||
477 | if ((number_of_items == 0) || (param == NULL)) | ||
478 | return; | ||
479 | for (i = 0; i < number_of_items; i++) { | ||
480 | kfree(param[i].path_name); | ||
481 | kfree(param[i].node_name); | ||
482 | } | ||
483 | kfree(param); | ||
484 | } | ||
485 | |||
463 | #define MID_FREE 0 | 486 | #define MID_FREE 0 |
464 | #define MID_REQUEST_ALLOCATED 1 | 487 | #define MID_REQUEST_ALLOCATED 1 |
465 | #define MID_REQUEST_SUBMITTED 2 | 488 | #define MID_REQUEST_SUBMITTED 2 |
diff --git a/fs/cifs/cifsproto.h b/fs/cifs/cifsproto.h index aaaf748f6a26..2f09f565a3d9 100644 --- a/fs/cifs/cifsproto.h +++ b/fs/cifs/cifsproto.h | |||
@@ -1,7 +1,7 @@ | |||
1 | /* | 1 | /* |
2 | * fs/cifs/cifsproto.h | 2 | * fs/cifs/cifsproto.h |
3 | * | 3 | * |
4 | * Copyright (c) International Business Machines Corp., 2002,2007 | 4 | * Copyright (c) International Business Machines Corp., 2002,2008 |
5 | * Author(s): Steve French (sfrench@us.ibm.com) | 5 | * Author(s): Steve French (sfrench@us.ibm.com) |
6 | * | 6 | * |
7 | * This library is free software; you can redistribute it and/or modify | 7 | * This library is free software; you can redistribute it and/or modify |
@@ -156,7 +156,7 @@ extern int get_dfs_path(int xid, struct cifsSesInfo *pSesInfo, | |||
156 | const char *old_path, | 156 | const char *old_path, |
157 | const struct nls_table *nls_codepage, | 157 | const struct nls_table *nls_codepage, |
158 | unsigned int *pnum_referrals, | 158 | unsigned int *pnum_referrals, |
159 | unsigned char **preferrals, | 159 | struct dfs_info3_param **preferrals, |
160 | int remap); | 160 | int remap); |
161 | extern void reset_cifs_unix_caps(int xid, struct cifsTconInfo *tcon, | 161 | extern void reset_cifs_unix_caps(int xid, struct cifsTconInfo *tcon, |
162 | struct super_block *sb, struct smb_vol *vol); | 162 | struct super_block *sb, struct smb_vol *vol); |
diff --git a/fs/cifs/connect.c b/fs/cifs/connect.c index db3746c891b5..65d0ba72e78f 100644 --- a/fs/cifs/connect.c +++ b/fs/cifs/connect.c | |||
@@ -1,7 +1,7 @@ | |||
1 | /* | 1 | /* |
2 | * fs/cifs/connect.c | 2 | * fs/cifs/connect.c |
3 | * | 3 | * |
4 | * Copyright (C) International Business Machines Corp., 2002,2007 | 4 | * Copyright (C) International Business Machines Corp., 2002,2008 |
5 | * Author(s): Steve French (sfrench@us.ibm.com) | 5 | * Author(s): Steve French (sfrench@us.ibm.com) |
6 | * | 6 | * |
7 | * This library is free software; you can redistribute it and/or modify | 7 | * This library is free software; you can redistribute it and/or modify |
@@ -1410,7 +1410,7 @@ connect_to_dfs_path(int xid, struct cifsSesInfo *pSesInfo, | |||
1410 | const char *old_path, const struct nls_table *nls_codepage, | 1410 | const char *old_path, const struct nls_table *nls_codepage, |
1411 | int remap) | 1411 | int remap) |
1412 | { | 1412 | { |
1413 | unsigned char *referrals = NULL; | 1413 | struct dfs_info3_param *referrals = NULL; |
1414 | unsigned int num_referrals; | 1414 | unsigned int num_referrals; |
1415 | int rc = 0; | 1415 | int rc = 0; |
1416 | 1416 | ||
@@ -1429,12 +1429,14 @@ connect_to_dfs_path(int xid, struct cifsSesInfo *pSesInfo, | |||
1429 | int | 1429 | int |
1430 | get_dfs_path(int xid, struct cifsSesInfo *pSesInfo, const char *old_path, | 1430 | get_dfs_path(int xid, struct cifsSesInfo *pSesInfo, const char *old_path, |
1431 | const struct nls_table *nls_codepage, unsigned int *pnum_referrals, | 1431 | const struct nls_table *nls_codepage, unsigned int *pnum_referrals, |
1432 | unsigned char **preferrals, int remap) | 1432 | struct dfs_info3_param **preferrals, int remap) |
1433 | { | 1433 | { |
1434 | char *temp_unc; | 1434 | char *temp_unc; |
1435 | int rc = 0; | 1435 | int rc = 0; |
1436 | unsigned char *targetUNCs; | ||
1436 | 1437 | ||
1437 | *pnum_referrals = 0; | 1438 | *pnum_referrals = 0; |
1439 | *preferrals = NULL; | ||
1438 | 1440 | ||
1439 | if (pSesInfo->ipc_tid == 0) { | 1441 | if (pSesInfo->ipc_tid == 0) { |
1440 | temp_unc = kmalloc(2 /* for slashes */ + | 1442 | temp_unc = kmalloc(2 /* for slashes */ + |
@@ -1454,8 +1456,10 @@ get_dfs_path(int xid, struct cifsSesInfo *pSesInfo, const char *old_path, | |||
1454 | kfree(temp_unc); | 1456 | kfree(temp_unc); |
1455 | } | 1457 | } |
1456 | if (rc == 0) | 1458 | if (rc == 0) |
1457 | rc = CIFSGetDFSRefer(xid, pSesInfo, old_path, preferrals, | 1459 | rc = CIFSGetDFSRefer(xid, pSesInfo, old_path, &targetUNCs, |
1458 | pnum_referrals, nls_codepage, remap); | 1460 | pnum_referrals, nls_codepage, remap); |
1461 | /* BB map targetUNCs to dfs_info3 structures, here or | ||
1462 | in CIFSGetDFSRefer BB */ | ||
1459 | 1463 | ||
1460 | return rc; | 1464 | return rc; |
1461 | } | 1465 | } |
diff --git a/fs/cifs/dns_resolve.c b/fs/cifs/dns_resolve.c index 777a086abd6f..ef7f43824347 100644 --- a/fs/cifs/dns_resolve.c +++ b/fs/cifs/dns_resolve.c | |||
@@ -64,13 +64,14 @@ struct key_type key_type_dns_resolver = { | |||
64 | * return 0 on success | 64 | * return 0 on success |
65 | */ | 65 | */ |
66 | int | 66 | int |
67 | dns_resolve_server_name_to_ip(const char *unc, char **ip_addr) { | 67 | dns_resolve_server_name_to_ip(const char *unc, char **ip_addr) |
68 | { | ||
68 | int rc = -EAGAIN; | 69 | int rc = -EAGAIN; |
69 | struct key *rkey; | 70 | struct key *rkey; |
70 | char *name; | 71 | char *name; |
71 | int len; | 72 | int len; |
72 | 73 | ||
73 | if ((!ip_addr) || (!unc)) | 74 | if (!ip_addr || !unc) |
74 | return -EINVAL; | 75 | return -EINVAL; |
75 | 76 | ||
76 | /* search for server name delimiter */ | 77 | /* search for server name delimiter */ |
diff --git a/fs/cifs/link.c b/fs/cifs/link.c index 11f265726db7..1d6fb01b8e6d 100644 --- a/fs/cifs/link.c +++ b/fs/cifs/link.c | |||
@@ -1,7 +1,7 @@ | |||
1 | /* | 1 | /* |
2 | * fs/cifs/link.c | 2 | * fs/cifs/link.c |
3 | * | 3 | * |
4 | * Copyright (C) International Business Machines Corp., 2002,2003 | 4 | * Copyright (C) International Business Machines Corp., 2002,2008 |
5 | * Author(s): Steve French (sfrench@us.ibm.com) | 5 | * Author(s): Steve French (sfrench@us.ibm.com) |
6 | * | 6 | * |
7 | * This library is free software; you can redistribute it and/or modify | 7 | * This library is free software; you can redistribute it and/or modify |
@@ -236,8 +236,6 @@ cifs_readlink(struct dentry *direntry, char __user *pBuffer, int buflen) | |||
236 | char *full_path = NULL; | 236 | char *full_path = NULL; |
237 | char *tmp_path = NULL; | 237 | char *tmp_path = NULL; |
238 | char *tmpbuffer; | 238 | char *tmpbuffer; |
239 | unsigned char *referrals = NULL; | ||
240 | unsigned int num_referrals = 0; | ||
241 | int len; | 239 | int len; |
242 | __u16 fid; | 240 | __u16 fid; |
243 | 241 | ||
@@ -297,8 +295,11 @@ cifs_readlink(struct dentry *direntry, char __user *pBuffer, int buflen) | |||
297 | cFYI(1, ("Error closing junction point " | 295 | cFYI(1, ("Error closing junction point " |
298 | "(open for ioctl)")); | 296 | "(open for ioctl)")); |
299 | } | 297 | } |
298 | /* BB unwind this long, nested function, or remove BB */ | ||
300 | if (rc == -EIO) { | 299 | if (rc == -EIO) { |
301 | /* Query if DFS Junction */ | 300 | /* Query if DFS Junction */ |
301 | unsigned int num_referrals = 0; | ||
302 | struct dfs_info3_param *refs = NULL; | ||
302 | tmp_path = | 303 | tmp_path = |
303 | kmalloc(MAX_TREE_SIZE + MAX_PATHCONF + 1, | 304 | kmalloc(MAX_TREE_SIZE + MAX_PATHCONF + 1, |
304 | GFP_KERNEL); | 305 | GFP_KERNEL); |
@@ -310,7 +311,7 @@ cifs_readlink(struct dentry *direntry, char __user *pBuffer, int buflen) | |||
310 | rc = get_dfs_path(xid, pTcon->ses, | 311 | rc = get_dfs_path(xid, pTcon->ses, |
311 | tmp_path, | 312 | tmp_path, |
312 | cifs_sb->local_nls, | 313 | cifs_sb->local_nls, |
313 | &num_referrals, &referrals, | 314 | &num_referrals, &refs, |
314 | cifs_sb->mnt_cifs_flags & | 315 | cifs_sb->mnt_cifs_flags & |
315 | CIFS_MOUNT_MAP_SPECIAL_CHR); | 316 | CIFS_MOUNT_MAP_SPECIAL_CHR); |
316 | cFYI(1, ("Get DFS for %s rc = %d ", | 317 | cFYI(1, ("Get DFS for %s rc = %d ", |
@@ -320,14 +321,13 @@ cifs_readlink(struct dentry *direntry, char __user *pBuffer, int buflen) | |||
320 | else { | 321 | else { |
321 | cFYI(1, ("num referral: %d", | 322 | cFYI(1, ("num referral: %d", |
322 | num_referrals)); | 323 | num_referrals)); |
323 | if (referrals) { | 324 | if (refs && refs->path_name) { |
324 | cFYI(1,("referral string: %s", referrals)); | ||
325 | strncpy(tmpbuffer, | 325 | strncpy(tmpbuffer, |
326 | referrals, | 326 | refs->path_name, |
327 | len-1); | 327 | len-1); |
328 | } | 328 | } |
329 | } | 329 | } |
330 | kfree(referrals); | 330 | kfree(refs); |
331 | kfree(tmp_path); | 331 | kfree(tmp_path); |
332 | } | 332 | } |
333 | /* BB add code like else decode referrals | 333 | /* BB add code like else decode referrals |