From a761ac579b89bc1f00212a42401398108deba65c Mon Sep 17 00:00:00 2001 From: Steve French Date: Thu, 18 Oct 2007 21:45:27 +0000 Subject: [PATCH] [CIFS] log better errors on failed mounts Also returns more accurate errors to mount for the cases of account expired and password expired Acked-by: Jeff Layton Signed-off-by: Steve French --- fs/cifs/cifsproto.h | 5 +++-- fs/cifs/cifssmb.c | 10 +++++----- fs/cifs/netmisc.c | 28 ++++++++++++++++++---------- fs/cifs/sess.c | 3 ++- fs/cifs/smberr.h | 5 +++-- fs/cifs/transport.c | 10 ++++------ 6 files changed, 35 insertions(+), 26 deletions(-) diff --git a/fs/cifs/cifsproto.h b/fs/cifs/cifsproto.h index 001f0dc7e6..1a883663b2 100644 --- a/fs/cifs/cifsproto.h +++ b/fs/cifs/cifsproto.h @@ -50,7 +50,8 @@ extern int SendReceive(const unsigned int /* xid */ , struct cifsSesInfo *, int * /* bytes returned */ , const int long_op); extern int SendReceive2(const unsigned int /* xid */ , struct cifsSesInfo *, struct kvec *, int /* nvec to send */, - int * /* type of buf returned */ , const int long_op); + int * /* type of buf returned */ , const int long_op, + const int logError /* whether to log status code*/ ); extern int SendReceiveBlockingLock(const unsigned int /* xid */ , struct cifsTconInfo *, struct smb_hdr * /* input */ , @@ -65,7 +66,7 @@ extern unsigned int smbCalcSize_LE(struct smb_hdr *ptr); extern int decode_negTokenInit(unsigned char *security_blob, int length, enum securityEnum *secType); extern int cifs_inet_pton(int, char *source, void *dst); -extern int map_smb_to_linux_error(struct smb_hdr *smb); +extern int map_smb_to_linux_error(struct smb_hdr *smb, int logErr); extern void header_assemble(struct smb_hdr *, char /* command */ , const struct cifsTconInfo *, int /* length of fixed section (word count) in two byte units */); diff --git a/fs/cifs/cifssmb.c b/fs/cifs/cifssmb.c index 2b2d4fec36..f0d9a485d0 100644 --- a/fs/cifs/cifssmb.c +++ b/fs/cifs/cifssmb.c @@ -1446,9 +1446,8 @@ CIFSSMBRead(const int xid, struct cifsTconInfo *tcon, const int netfid, iov[0].iov_base = (char *)pSMB; iov[0].iov_len = pSMB->hdr.smb_buf_length + 4; - rc = SendReceive2(xid, tcon->ses, iov, - 1 /* num iovecs */, - &resp_buf_type, 0); + rc = SendReceive2(xid, tcon->ses, iov, 1 /* num iovecs */, + &resp_buf_type, 0 /* not long op */, 1 /* log err */ ); cifs_stats_inc(&tcon->num_reads); pSMBr = (READ_RSP *)iov[0].iov_base; if (rc) { @@ -1667,7 +1666,7 @@ CIFSSMBWrite2(const int xid, struct cifsTconInfo *tcon, rc = SendReceive2(xid, tcon->ses, iov, n_vec + 1, &resp_buf_type, - long_op); + long_op, 0 /* do not log STATUS code */ ); cifs_stats_inc(&tcon->num_writes); if (rc) { cFYI(1, ("Send error Write2 = %d", rc)); @@ -3094,7 +3093,8 @@ CIFSSMBGetCIFSACL(const int xid, struct cifsTconInfo *tcon, __u16 fid, iov[0].iov_base = (char *)pSMB; iov[0].iov_len = pSMB->hdr.smb_buf_length + 4; - rc = SendReceive2(xid, tcon->ses, iov, 1 /* num iovec */, &buf_type, 0); + rc = SendReceive2(xid, tcon->ses, iov, 1 /* num iovec */, &buf_type, + 0 /* not long op */, 0 /* do not log STATUS codes */ ); cifs_stats_inc(&tcon->num_acl_get); if (rc) { cFYI(1, ("Send error in QuerySecDesc = %d", rc)); diff --git a/fs/cifs/netmisc.c b/fs/cifs/netmisc.c index 9ae4941cd6..f06359cb22 100644 --- a/fs/cifs/netmisc.c +++ b/fs/cifs/netmisc.c @@ -114,10 +114,16 @@ static const struct smb_to_posix_error mapping_table_ERRSRV[] = { {ERRusempx, -EIO}, {ERRusestd, -EIO}, {ERR_NOTIFY_ENUM_DIR, -ENOBUFS}, - {ERRaccountexpired, -EACCES}, + {ERRnoSuchUser, -EACCES}, +/* {ERRaccountexpired, -EACCES}, {ERRbadclient, -EACCES}, {ERRbadLogonTime, -EACCES}, - {ERRpasswordExpired, -EACCES}, + {ERRpasswordExpired, -EACCES},*/ + {ERRaccountexpired, -EKEYEXPIRED}, + {ERRbadclient, -EACCES}, + {ERRbadLogonTime, -EACCES}, + {ERRpasswordExpired, -EKEYEXPIRED}, + {ERRnosupport, -EINVAL}, {0, 0} }; @@ -270,7 +276,7 @@ static const struct { from NT_STATUS_NO_SUCH_USER to NT_STATUS_LOGON_FAILURE during the session setup } */ { - ERRDOS, ERRnoaccess, NT_STATUS_NO_SUCH_USER}, { + ERRDOS, ERRnoaccess, NT_STATUS_NO_SUCH_USER}, { /* could map to 2238 */ ERRHRD, ERRgeneral, NT_STATUS_GROUP_EXISTS}, { ERRHRD, ERRgeneral, NT_STATUS_NO_SUCH_GROUP}, { ERRHRD, ERRgeneral, NT_STATUS_MEMBER_IN_GROUP}, { @@ -285,10 +291,10 @@ static const struct { ERRHRD, ERRgeneral, NT_STATUS_PASSWORD_RESTRICTION}, { ERRDOS, ERRnoaccess, NT_STATUS_LOGON_FAILURE}, { ERRHRD, ERRgeneral, NT_STATUS_ACCOUNT_RESTRICTION}, { - ERRSRV, 2241, NT_STATUS_INVALID_LOGON_HOURS}, { - ERRSRV, 2240, NT_STATUS_INVALID_WORKSTATION}, { + ERRSRV, ERRbadLogonTime, NT_STATUS_INVALID_LOGON_HOURS}, { + ERRSRV, ERRbadclient, NT_STATUS_INVALID_WORKSTATION}, { ERRSRV, ERRpasswordExpired, NT_STATUS_PASSWORD_EXPIRED}, { - ERRSRV, 2239, NT_STATUS_ACCOUNT_DISABLED}, { + ERRSRV, ERRaccountexpired, NT_STATUS_ACCOUNT_DISABLED}, { ERRHRD, ERRgeneral, NT_STATUS_NONE_MAPPED}, { ERRHRD, ERRgeneral, NT_STATUS_TOO_MANY_LUIDS_REQUESTED}, { ERRHRD, ERRgeneral, NT_STATUS_LUIDS_EXHAUSTED}, { @@ -585,7 +591,7 @@ static const struct { ERRDOS, ERRnoaccess, NT_STATUS_TRUST_FAILURE}, { ERRHRD, ERRgeneral, NT_STATUS_MUTANT_LIMIT_EXCEEDED}, { ERRDOS, ERRnetlogonNotStarted, NT_STATUS_NETLOGON_NOT_STARTED}, { - ERRSRV, 2239, NT_STATUS_ACCOUNT_EXPIRED}, { + ERRSRV, ERRaccountexpired, NT_STATUS_ACCOUNT_EXPIRED}, { ERRHRD, ERRgeneral, NT_STATUS_POSSIBLE_DEADLOCK}, { ERRHRD, ERRgeneral, NT_STATUS_NETWORK_CREDENTIAL_CONFLICT}, { ERRHRD, ERRgeneral, NT_STATUS_REMOTE_SESSION_LIMIT}, { @@ -754,7 +760,7 @@ ntstatus_to_dos(__u32 ntstatus, __u8 * eclass, __u16 * ecode) } int -map_smb_to_linux_error(struct smb_hdr *smb) +map_smb_to_linux_error(struct smb_hdr *smb, int logErr) { unsigned int i; int rc = -EIO; /* if transport error smb error may not be set */ @@ -771,7 +777,9 @@ map_smb_to_linux_error(struct smb_hdr *smb) /* translate the newer STATUS codes to old style SMB errors * and then to POSIX errors */ __u32 err = le32_to_cpu(smb->Status.CifsError); - if (cifsFYI & CIFS_RC) + if (logErr && (err != (NT_STATUS_MORE_PROCESSING_REQUIRED))) + cifs_print_status(err); + else if (cifsFYI & CIFS_RC) cifs_print_status(err); ntstatus_to_dos(err, &smberrclass, &smberrcode); } else { @@ -813,7 +821,7 @@ map_smb_to_linux_error(struct smb_hdr *smb) } /* else ERRHRD class errors or junk - return EIO */ - cFYI(1, (" !!Mapping smb error code %d to POSIX err %d !!", + cFYI(1, ("Mapping smb error code %d to POSIX err %d", smberrcode, rc)); /* generic corrective action e.g. reconnect SMB session on diff --git a/fs/cifs/sess.c b/fs/cifs/sess.c index c74a064e78..899dc6078d 100644 --- a/fs/cifs/sess.c +++ b/fs/cifs/sess.c @@ -513,7 +513,8 @@ CIFS_SessSetup(unsigned int xid, struct cifsSesInfo *ses, int first_time, iov[1].iov_base = str_area; iov[1].iov_len = count; - rc = SendReceive2(xid, ses, iov, 2 /* num_iovecs */, &resp_buf_type, 0); + rc = SendReceive2(xid, ses, iov, 2 /* num_iovecs */, &resp_buf_type, + 0 /* not long op */, 1 /* log NT STATUS if any */ ); /* SMB request buf freed in SendReceive2 */ cFYI(1, ("ssetup rc from sendrecv2 is %d", rc)); diff --git a/fs/cifs/smberr.h b/fs/cifs/smberr.h index 2ef0be2888..7f50e8577c 100644 --- a/fs/cifs/smberr.h +++ b/fs/cifs/smberr.h @@ -173,9 +173,10 @@ #define ERRusestd 251 /* temporarily unable to use either raw or mpx */ #define ERR_NOTIFY_ENUM_DIR 1024 +#define ERRnoSuchUser 2238 /* user account does not exist */ #define ERRaccountexpired 2239 -#define ERRbadclient 2240 -#define ERRbadLogonTime 2241 +#define ERRbadclient 2240 /* can not logon from this client */ +#define ERRbadLogonTime 2241 /* logon hours do not allow this */ #define ERRpasswordExpired 2242 #define ERRnetlogonNotStarted 2455 #define ERRnosupport 0xFFFF diff --git a/fs/cifs/transport.c b/fs/cifs/transport.c index 6684926bf3..7ed32b3cb7 100644 --- a/fs/cifs/transport.c +++ b/fs/cifs/transport.c @@ -418,7 +418,7 @@ static int wait_for_response(struct cifsSesInfo *ses, int SendReceive2(const unsigned int xid, struct cifsSesInfo *ses, struct kvec *iov, int n_vec, int *pRespBufType /* ret */, - const int long_op) + const int long_op, const int logError) { int rc = 0; unsigned int receive_len; @@ -464,7 +464,6 @@ SendReceive2(const unsigned int xid, struct cifsSesInfo *ses, wake_up(&ses->server->request_q); return rc; } - rc = cifs_sign_smb2(iov, n_vec, ses->server, &midQ->sequence_number); midQ->midState = MID_REQUEST_SUBMITTED; @@ -567,8 +566,7 @@ SendReceive2(const unsigned int xid, struct cifsSesInfo *ses, } /* BB special case reconnect tid and uid here? */ - /* BB special case Errbadpassword and pwdexpired here */ - rc = map_smb_to_linux_error(midQ->resp_buf); + rc = map_smb_to_linux_error(midQ->resp_buf, logError); /* convert ByteCount if necessary */ if (receive_len >= sizeof(struct smb_hdr) - 4 @@ -747,7 +745,7 @@ SendReceive(const unsigned int xid, struct cifsSesInfo *ses, *pbytes_returned = out_buf->smb_buf_length; /* BB special case reconnect tid and uid here? */ - rc = map_smb_to_linux_error(out_buf); + rc = map_smb_to_linux_error(out_buf, 0 /* no log */ ); /* convert ByteCount if necessary */ if (receive_len >= sizeof(struct smb_hdr) - 4 @@ -990,7 +988,7 @@ SendReceiveBlockingLock(const unsigned int xid, struct cifsTconInfo *tcon, *pbytes_returned = out_buf->smb_buf_length; /* BB special case reconnect tid and uid here? */ - rc = map_smb_to_linux_error(out_buf); + rc = map_smb_to_linux_error(out_buf, 0 /* no log */ ); /* convert ByteCount if necessary */ if (receive_len >= sizeof(struct smb_hdr) - 4 -- 2.39.5