Skip to content

Commit

Permalink
cifs: Create a new shared file holding smb2 pdu definitions
Browse files Browse the repository at this point in the history
This file will contain all the definitions we need for SMB2 packets
and will follow the naming convention of MS-SMB2.PDF as closely
as possible to make it easier to cross-reference beween the definitions
and the standard.

The content of this file will mostly consist of migration of existing
definitions in the cifs/smb2.pdu.h and ksmbd/smb2pdu.h files
with some additional tweaks as the two files have diverged.

This patch introduces the new smbfs_common/smb2pdu.h file
and migrates the SMB2 header as well as TREE_CONNECT and TREE_DISCONNECT
to the shared file.

Signed-off-by: Ronnie Sahlberg <lsahlber@redhat.com>
Reviewed-by: Namjae Jeon <linkinjeon@kernel.org>
Signed-off-by: Steve French <stfrench@microsoft.com>
  • Loading branch information
Ronnie Sahlberg authored and Steve French committed Nov 5, 2021
1 parent 7ae5e58 commit 0d35e38
Show file tree
Hide file tree
Showing 12 changed files with 493 additions and 476 deletions.
1 change: 0 additions & 1 deletion fs/cifs/cifsfs.c
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,6 @@
#include <linux/key-type.h>
#include "cifs_spnego.h"
#include "fscache.h"
#include "smb2pdu.h"
#ifdef CONFIG_CIFS_DFS_UPCALL
#include "dfs_cache.h"
#endif
Expand Down
3 changes: 2 additions & 1 deletion fs/cifs/cifsglob.h
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
#include <crypto/internal/hash.h>
#include <linux/scatterlist.h>
#include <uapi/linux/cifs/cifs_mount.h>
#include "../smbfs_common/smb2pdu.h"
#include "smb2pdu.h"

#define CIFS_MAGIC_NUMBER 0xFF534D42 /* the first four bytes of SMB PDUs */
Expand Down Expand Up @@ -776,7 +777,7 @@ revert_current_mid(struct TCP_Server_Info *server, const unsigned int val)

static inline void
revert_current_mid_from_hdr(struct TCP_Server_Info *server,
const struct smb2_sync_hdr *shdr)
const struct smb2_hdr *shdr)
{
unsigned int num = le16_to_cpu(shdr->CreditCharge);

Expand Down
4 changes: 2 additions & 2 deletions fs/cifs/connect.c
Original file line number Diff line number Diff line change
Expand Up @@ -677,7 +677,7 @@ dequeue_mid(struct mid_q_entry *mid, bool malformed)
static unsigned int
smb2_get_credits_from_hdr(char *buffer, struct TCP_Server_Info *server)
{
struct smb2_sync_hdr *shdr = (struct smb2_sync_hdr *)buffer;
struct smb2_hdr *shdr = (struct smb2_hdr *)buffer;

/*
* SMB1 does not use credits.
Expand Down Expand Up @@ -877,7 +877,7 @@ cifs_handle_standard(struct TCP_Server_Info *server, struct mid_q_entry *mid)
static void
smb2_add_credits_from_hdr(char *buffer, struct TCP_Server_Info *server)
{
struct smb2_sync_hdr *shdr = (struct smb2_sync_hdr *)buffer;
struct smb2_hdr *shdr = (struct smb2_hdr *)buffer;
int scredits, in_flight;

/*
Expand Down
2 changes: 1 addition & 1 deletion fs/cifs/misc.c
Original file line number Diff line number Diff line change
Expand Up @@ -152,7 +152,7 @@ cifs_buf_get(void)
* SMB2 header is bigger than CIFS one - no problems to clean some
* more bytes for CIFS.
*/
size_t buf_size = sizeof(struct smb2_sync_hdr);
size_t buf_size = sizeof(struct smb2_hdr);

/*
* We could use negotiated size instead of max_msgsize -
Expand Down
16 changes: 10 additions & 6 deletions fs/cifs/smb2maperror.c
Original file line number Diff line number Diff line change
Expand Up @@ -2439,14 +2439,16 @@ smb2_print_status(__le32 status)
int
map_smb2_to_linux_error(char *buf, bool log_err)
{
struct smb2_sync_hdr *shdr = (struct smb2_sync_hdr *)buf;
struct smb2_hdr *shdr = (struct smb2_hdr *)buf;
unsigned int i;
int rc = -EIO;
__le32 smb2err = shdr->Status;

if (smb2err == 0) {
trace_smb3_cmd_done(shdr->TreeId, shdr->SessionId,
le16_to_cpu(shdr->Command), le64_to_cpu(shdr->MessageId));
trace_smb3_cmd_done(le32_to_cpu(shdr->Id.SyncId.TreeId),
le64_to_cpu(shdr->SessionId),
le16_to_cpu(shdr->Command),
le64_to_cpu(shdr->MessageId));
return 0;
}

Expand All @@ -2470,8 +2472,10 @@ map_smb2_to_linux_error(char *buf, bool log_err)
cifs_dbg(FYI, "Mapping SMB2 status code 0x%08x to POSIX err %d\n",
__le32_to_cpu(smb2err), rc);

trace_smb3_cmd_err(shdr->TreeId, shdr->SessionId,
le16_to_cpu(shdr->Command),
le64_to_cpu(shdr->MessageId), le32_to_cpu(smb2err), rc);
trace_smb3_cmd_err(le32_to_cpu(shdr->Id.SyncId.TreeId),
le64_to_cpu(shdr->SessionId),
le16_to_cpu(shdr->Command),
le64_to_cpu(shdr->MessageId),
le32_to_cpu(smb2err), rc);
return rc;
}
43 changes: 21 additions & 22 deletions fs/cifs/smb2misc.c
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,6 @@
*
*/
#include <linux/ctype.h>
#include "smb2pdu.h"
#include "cifsglob.h"
#include "cifsproto.h"
#include "smb2proto.h"
Expand All @@ -19,7 +18,7 @@
#include "nterr.h"

static int
check_smb2_hdr(struct smb2_sync_hdr *shdr, __u64 mid)
check_smb2_hdr(struct smb2_hdr *shdr, __u64 mid)
{
__u64 wire_mid = le64_to_cpu(shdr->MessageId);

Expand Down Expand Up @@ -81,9 +80,9 @@ static const __le16 smb2_rsp_struct_sizes[NUMBER_OF_SMB2_COMMANDS] = {
/* SMB2_OPLOCK_BREAK */ cpu_to_le16(24)
};

#define SMB311_NEGPROT_BASE_SIZE (sizeof(struct smb2_sync_hdr) + sizeof(struct smb2_negotiate_rsp))
#define SMB311_NEGPROT_BASE_SIZE (sizeof(struct smb2_hdr) + sizeof(struct smb2_negotiate_rsp))

static __u32 get_neg_ctxt_len(struct smb2_sync_hdr *hdr, __u32 len,
static __u32 get_neg_ctxt_len(struct smb2_hdr *hdr, __u32 len,
__u32 non_ctxlen)
{
__u16 neg_count;
Expand Down Expand Up @@ -135,13 +134,13 @@ static __u32 get_neg_ctxt_len(struct smb2_sync_hdr *hdr, __u32 len,
int
smb2_check_message(char *buf, unsigned int len, struct TCP_Server_Info *srvr)
{
struct smb2_sync_hdr *shdr = (struct smb2_sync_hdr *)buf;
struct smb2_sync_pdu *pdu = (struct smb2_sync_pdu *)shdr;
struct smb2_hdr *shdr = (struct smb2_hdr *)buf;
struct smb2_pdu *pdu = (struct smb2_pdu *)shdr;
__u64 mid;
__u32 clc_len; /* calculated length */
int command;
int pdu_size = sizeof(struct smb2_sync_pdu);
int hdr_size = sizeof(struct smb2_sync_hdr);
int pdu_size = sizeof(struct smb2_pdu);
int hdr_size = sizeof(struct smb2_hdr);

/*
* Add function to do table lookup of StructureSize by command
Expand All @@ -155,7 +154,7 @@ smb2_check_message(char *buf, unsigned int len, struct TCP_Server_Info *srvr)
/* decrypt frame now that it is completely read in */
spin_lock(&cifs_tcp_ses_lock);
list_for_each_entry(ses, &srvr->smb_ses_list, smb_ses_list) {
if (ses->Suid == thdr->SessionId)
if (ses->Suid == le64_to_cpu(thdr->SessionId))
break;
}
spin_unlock(&cifs_tcp_ses_lock);
Expand Down Expand Up @@ -296,7 +295,7 @@ static const bool has_smb2_data_area[NUMBER_OF_SMB2_COMMANDS] = {
* area and the offset to it (from the beginning of the smb are also returned.
*/
char *
smb2_get_data_area_len(int *off, int *len, struct smb2_sync_hdr *shdr)
smb2_get_data_area_len(int *off, int *len, struct smb2_hdr *shdr)
{
*off = 0;
*len = 0;
Expand Down Expand Up @@ -401,8 +400,8 @@ smb2_get_data_area_len(int *off, int *len, struct smb2_sync_hdr *shdr)
unsigned int
smb2_calc_size(void *buf, struct TCP_Server_Info *srvr)
{
struct smb2_sync_pdu *pdu = (struct smb2_sync_pdu *)buf;
struct smb2_sync_hdr *shdr = &pdu->sync_hdr;
struct smb2_pdu *pdu = (struct smb2_pdu *)buf;
struct smb2_hdr *shdr = &pdu->hdr;
int offset; /* the offset from the beginning of SMB to data area */
int data_length; /* the length of the variable length data area */
/* Structure Size has already been checked to make sure it is 64 */
Expand Down Expand Up @@ -669,7 +668,7 @@ smb2_is_valid_oplock_break(char *buffer, struct TCP_Server_Info *server)

cifs_dbg(FYI, "Checking for oplock break\n");

if (rsp->sync_hdr.Command != SMB2_OPLOCK_BREAK)
if (rsp->hdr.Command != SMB2_OPLOCK_BREAK)
return false;

if (rsp->StructureSize !=
Expand Down Expand Up @@ -816,23 +815,23 @@ smb2_handle_cancelled_close(struct cifs_tcon *tcon, __u64 persistent_fid,
int
smb2_handle_cancelled_mid(struct mid_q_entry *mid, struct TCP_Server_Info *server)
{
struct smb2_sync_hdr *sync_hdr = mid->resp_buf;
struct smb2_hdr *hdr = mid->resp_buf;
struct smb2_create_rsp *rsp = mid->resp_buf;
struct cifs_tcon *tcon;
int rc;

if ((mid->optype & CIFS_CP_CREATE_CLOSE_OP) || sync_hdr->Command != SMB2_CREATE ||
sync_hdr->Status != STATUS_SUCCESS)
if ((mid->optype & CIFS_CP_CREATE_CLOSE_OP) || hdr->Command != SMB2_CREATE ||
hdr->Status != STATUS_SUCCESS)
return 0;

tcon = smb2_find_smb_tcon(server, sync_hdr->SessionId,
sync_hdr->TreeId);
tcon = smb2_find_smb_tcon(server, le64_to_cpu(hdr->SessionId),
le32_to_cpu(hdr->Id.SyncId.TreeId));
if (!tcon)
return -ENOENT;

rc = __smb2_handle_cancelled_cmd(tcon,
le16_to_cpu(sync_hdr->Command),
le64_to_cpu(sync_hdr->MessageId),
le16_to_cpu(hdr->Command),
le64_to_cpu(hdr->MessageId),
rsp->PersistentFileId,
rsp->VolatileFileId);
if (rc)
Expand All @@ -856,10 +855,10 @@ smb311_update_preauth_hash(struct cifs_ses *ses, struct kvec *iov, int nvec)
{
int i, rc;
struct sdesc *d;
struct smb2_sync_hdr *hdr;
struct smb2_hdr *hdr;
struct TCP_Server_Info *server = cifs_ses_server(ses);

hdr = (struct smb2_sync_hdr *)iov[0].iov_base;
hdr = (struct smb2_hdr *)iov[0].iov_base;
/* neg prot are always taken */
if (hdr->Command == SMB2_NEGOTIATE)
goto ok;
Expand Down
Loading

0 comments on commit 0d35e38

Please sign in to comment.