Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 1c3ddfe5 authored by Linus Torvalds's avatar Linus Torvalds
Browse files
Pull CIFS fixes from Steve French

* git://git.samba.org/sfrench/cifs-2.6:
  cifs: clean up ordering in exit_cifs
  cifs: clean up call to cifs_dfs_release_automount_timer()
  CIFS: Delete echo_retries module parm
  CIFS: Prepare credits code for a slot reservation
  CIFS: Make wait_for_free_request killable
  CIFS: Introduce credit-based flow control
  CIFS: Simplify inFlight logic
  cifs: fix issue mounting of DFS ROOT when redirecting from one domain controller to the next
  CIFS: Respect negotiated MaxMpxCount
  CIFS: Fix a spurious error in cifs_push_posix_locks
parents f63d395d 3dd93306
Loading
Loading
Loading
Loading
+1 −5
Original line number Diff line number Diff line
@@ -753,10 +753,6 @@ module loading or during the runtime by using the interface

i.e. echo "value" > /sys/module/cifs/parameters/<param>

1. echo_retries - The number of echo attempts before giving up and
		  reconnecting to the server. The default is 5. The value 0
		  means never reconnect.

2. enable_oplocks - Enable or disable oplocks. Oplocks are enabled by default.
1. enable_oplocks - Enable or disable oplocks. Oplocks are enabled by default.
		    [Y/y/1]. To disable use any of [N/n/0].
+1 −2
Original line number Diff line number Diff line
@@ -171,8 +171,7 @@ static int cifs_debug_data_proc_show(struct seq_file *m, void *v)
			seq_printf(m, "TCP status: %d\n\tLocal Users To "
				   "Server: %d SecMode: 0x%x Req On Wire: %d",
				   server->tcpStatus, server->srv_count,
				   server->sec_mode,
				   atomic_read(&server->inFlight));
				   server->sec_mode, in_flight(server));

#ifdef CONFIG_CIFS_STATS2
			seq_printf(m, " In Send: %d In MaxReq Wait: %d",
+9 −16
Original line number Diff line number Diff line
@@ -76,12 +76,7 @@ MODULE_PARM_DESC(cifs_min_small, "Small network buffers in pool. Default: 30 "
unsigned int cifs_max_pending = CIFS_MAX_REQ;
module_param(cifs_max_pending, int, 0444);
MODULE_PARM_DESC(cifs_max_pending, "Simultaneous requests to server. "
				   "Default: 50 Range: 2 to 256");
unsigned short echo_retries = 5;
module_param(echo_retries, ushort, 0644);
MODULE_PARM_DESC(echo_retries, "Number of echo attempts before giving up and "
			       "reconnecting server. Default: 5. 0 means "
			       "never reconnect.");
				   "Default: 32767 Range: 2 to 32767.");
module_param(enable_oplocks, bool, 0644);
MODULE_PARM_DESC(enable_oplocks, "Enable or disable oplocks (bool). Default:"
				 "y/Y/1");
@@ -1111,9 +1106,9 @@ init_cifs(void)
	if (cifs_max_pending < 2) {
		cifs_max_pending = 2;
		cFYI(1, "cifs_max_pending set to min of 2");
	} else if (cifs_max_pending > 256) {
		cifs_max_pending = 256;
		cFYI(1, "cifs_max_pending set to max of 256");
	} else if (cifs_max_pending > CIFS_MAX_REQ) {
		cifs_max_pending = CIFS_MAX_REQ;
		cFYI(1, "cifs_max_pending set to max of %u", CIFS_MAX_REQ);
	}

	rc = cifs_fscache_register();
@@ -1175,11 +1170,8 @@ static void __exit
exit_cifs(void)
{
	cFYI(DBG2, "exit_cifs");
	cifs_proc_clean();
	cifs_fscache_unregister();
#ifdef CONFIG_CIFS_DFS_UPCALL
	unregister_filesystem(&cifs_fs_type);
	cifs_dfs_release_automount_timer();
#endif
#ifdef CONFIG_CIFS_ACL
	cifs_destroy_idmaptrees();
	exit_cifs_idmap();
@@ -1187,10 +1179,11 @@ exit_cifs(void)
#ifdef CONFIG_CIFS_UPCALL
	unregister_key_type(&cifs_spnego_key_type);
#endif
	unregister_filesystem(&cifs_fs_type);
	cifs_destroy_inodecache();
	cifs_destroy_mids();
	cifs_destroy_request_bufs();
	cifs_destroy_mids();
	cifs_destroy_inodecache();
	cifs_fscache_unregister();
	cifs_proc_clean();
}

MODULE_AUTHOR("Steve French <sfrench@us.ibm.com>");
+36 −11
Original line number Diff line number Diff line
@@ -55,14 +55,9 @@

/*
 * MAX_REQ is the maximum number of requests that WE will send
 * on one socket concurrently. It also matches the most common
 * value of max multiplex returned by servers.  We may
 * eventually want to use the negotiated value (in case
 * future servers can handle more) when we are more confident that
 * we will not have problems oveloading the socket with pending
 * write data.
 * on one socket concurrently.
 */
#define CIFS_MAX_REQ 50
#define CIFS_MAX_REQ 32767

#define RFC1001_NAME_LEN 15
#define RFC1001_NAME_LEN_WITH_NULL (RFC1001_NAME_LEN + 1)
@@ -255,7 +250,9 @@ struct TCP_Server_Info {
	bool noblocksnd;		/* use blocking sendmsg */
	bool noautotune;		/* do not autotune send buf sizes */
	bool tcp_nodelay;
	atomic_t inFlight;  /* number of requests on the wire to server */
	int credits;  /* send no more requests at once */
	unsigned int in_flight;  /* number of requests on the wire to server */
	spinlock_t req_lock;  /* protect the two values above */
	struct mutex srv_mutex;
	struct task_struct *tsk;
	char server_GUID[16];
@@ -263,6 +260,7 @@ struct TCP_Server_Info {
	bool session_estab; /* mark when very first sess is established */
	u16 dialect; /* dialect index that server chose */
	enum securityEnum secType;
	bool oplocks:1; /* enable oplocks */
	unsigned int maxReq;	/* Clients should submit no more */
	/* than maxReq distinct unanswered SMBs to the server when using  */
	/* multiplexed reads or writes */
@@ -307,6 +305,36 @@ struct TCP_Server_Info {
#endif
};

static inline unsigned int
in_flight(struct TCP_Server_Info *server)
{
	unsigned int num;
	spin_lock(&server->req_lock);
	num = server->in_flight;
	spin_unlock(&server->req_lock);
	return num;
}

static inline int*
get_credits_field(struct TCP_Server_Info *server)
{
	/*
	 * This will change to switch statement when we reserve slots for echos
	 * and oplock breaks.
	 */
	return &server->credits;
}

static inline bool
has_credits(struct TCP_Server_Info *server, int *credits)
{
	int num;
	spin_lock(&server->req_lock);
	num = *credits;
	spin_unlock(&server->req_lock);
	return num > 0;
}

/*
 * Macros to allow the TCP_Server_Info->net field and related code to drop out
 * when CONFIG_NET_NS isn't set.
@@ -1010,9 +1038,6 @@ GLOBAL_EXTERN unsigned int cifs_min_rcv; /* min size of big ntwrk buf pool */
GLOBAL_EXTERN unsigned int cifs_min_small;  /* min size of small buf pool */
GLOBAL_EXTERN unsigned int cifs_max_pending; /* MAX requests at once to server*/

/* reconnect after this many failed echo attempts */
GLOBAL_EXTERN unsigned short echo_retries;

#ifdef CONFIG_CIFS_ACL
GLOBAL_EXTERN struct rb_root uidtree;
GLOBAL_EXTERN struct rb_root gidtree;
+9 −0
Original line number Diff line number Diff line
@@ -88,6 +88,9 @@ extern int SendReceiveBlockingLock(const unsigned int xid,
			struct smb_hdr *in_buf ,
			struct smb_hdr *out_buf,
			int *bytes_returned);
extern void cifs_add_credits(struct TCP_Server_Info *server,
			     const unsigned int add);
extern void cifs_set_credits(struct TCP_Server_Info *server, const int val);
extern int checkSMB(struct smb_hdr *smb, __u16 mid, unsigned int length);
extern bool is_valid_oplock_break(struct smb_hdr *smb,
				  struct TCP_Server_Info *);
@@ -168,7 +171,13 @@ extern struct smb_vol *cifs_get_volume_info(char *mount_data,
					    const char *devname);
extern int cifs_mount(struct cifs_sb_info *, struct smb_vol *);
extern void cifs_umount(struct cifs_sb_info *);

#if IS_ENABLED(CONFIG_CIFS_DFS_UPCALL)
extern void cifs_dfs_release_automount_timer(void);
#else /* ! IS_ENABLED(CONFIG_CIFS_DFS_UPCALL) */
#define cifs_dfs_release_automount_timer()	do { } while (0)
#endif /* ! IS_ENABLED(CONFIG_CIFS_DFS_UPCALL) */

void cifs_proc_init(void);
void cifs_proc_clean(void);

Loading