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

Commit 9094fad1 authored by Pavel Shilovsky's avatar Pavel Shilovsky
Browse files

CIFS: Add echo request support for SMB2

parent f6d76178
Loading
Loading
Loading
Loading
+3 −0
Original line number Diff line number Diff line
@@ -73,6 +73,9 @@
/*           (max path length + 1 for null) * 2 for unicode    */
#define MAX_NAME 514

/* SMB echo "timeout" -- FIXME: tunable? */
#define SMB_ECHO_INTERVAL (60 * HZ)

#include "cifspdu.h"

#ifndef XATTR_DOS_ATTRIB
+0 −3
Original line number Diff line number Diff line
@@ -56,9 +56,6 @@
#define CIFS_PORT 445
#define RFC1001_PORT 139

/* SMB echo "timeout" -- FIXME: tunable? */
#define SMB_ECHO_INTERVAL (60 * HZ)

extern mempool_t *cifs_req_poolp;

/* FIXME: should these be tunable? */
+8 −0
Original line number Diff line number Diff line
@@ -207,6 +207,12 @@ smb2_build_path_to_root(struct smb_vol *vol, struct cifs_sb_info *cifs_sb,
	return NULL;
}

static bool
smb2_can_echo(struct TCP_Server_Info *server)
{
	return server->echoes;
}

struct smb_version_operations smb21_operations = {
	.setup_request = smb2_setup_request,
	.setup_async_request = smb2_setup_async_request,
@@ -226,6 +232,8 @@ struct smb_version_operations smb21_operations = {
	.tree_connect = SMB2_tcon,
	.tree_disconnect = SMB2_tdis,
	.is_path_accessible = smb2_is_path_accessible,
	.can_echo = smb2_can_echo,
	.echo = SMB2_echo,
	.query_path_info = smb2_query_path_info,
	.get_srv_inum = smb2_get_srv_inum,
	.build_path_to_root = smb2_build_path_to_root,
+49 −0
Original line number Diff line number Diff line
@@ -1074,3 +1074,52 @@ SMB2_query_info(const unsigned int xid, struct cifs_tcon *tcon,
	free_rsp_buf(resp_buftype, rsp);
	return rc;
}

/*
 * This is a no-op for now. We're not really interested in the reply, but
 * rather in the fact that the server sent one and that server->lstrp
 * gets updated.
 *
 * FIXME: maybe we should consider checking that the reply matches request?
 */
static void
smb2_echo_callback(struct mid_q_entry *mid)
{
	struct TCP_Server_Info *server = mid->callback_data;
	struct smb2_echo_rsp *smb2 = (struct smb2_echo_rsp *)mid->resp_buf;
	unsigned int credits_received = 1;

	if (mid->mid_state == MID_RESPONSE_RECEIVED)
		credits_received = le16_to_cpu(smb2->hdr.CreditRequest);

	DeleteMidQEntry(mid);
	add_credits(server, credits_received, CIFS_ECHO_OP);
}

int
SMB2_echo(struct TCP_Server_Info *server)
{
	struct smb2_echo_req *req;
	int rc = 0;
	struct kvec iov;

	cFYI(1, "In echo request");

	rc = small_smb2_init(SMB2_ECHO, NULL, (void **)&req);
	if (rc)
		return rc;

	req->hdr.CreditRequest = cpu_to_le16(1);

	iov.iov_base = (char *)req;
	/* 4 for rfc1002 length field */
	iov.iov_len = get_rfc1002_length(req) + 4;

	rc = cifs_call_async(server, &iov, 1, NULL, smb2_echo_callback, server,
			     CIFS_ECHO_OP);
	if (rc)
		cFYI(1, "Echo request failed: %d", rc);

	cifs_small_buf_release(req);
	return rc;
}
+12 −0
Original line number Diff line number Diff line
@@ -448,6 +448,18 @@ struct smb2_close_rsp {
	__le32 Attributes;
} __packed;

struct smb2_echo_req {
	struct smb2_hdr hdr;
	__le16 StructureSize;	/* Must be 4 */
	__u16  Reserved;
} __packed;

struct smb2_echo_rsp {
	struct smb2_hdr hdr;
	__le16 StructureSize;	/* Must be 4 */
	__u16  Reserved;
} __packed;

/* Possible InfoType values */
#define SMB2_O_INFO_FILE	0x01
#define SMB2_O_INFO_FILESYSTEM	0x02
Loading