summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorEnzo Matsumiya <ematsumiya@suse.de>2024-11-13 19:00:57 -0300
committerEnzo Matsumiya <ematsumiya@suse.de>2024-11-14 15:54:44 -0300
commit53caeaa17cd267570de61424de306f6a6b4e14d0 (patch)
tree4038d35e9fe6d085c682d69a70603f7842ceb364
parenta10fb4913a4ad6d10166d1feba26fbc8b9deb322 (diff)
downloadlinux-53caeaa17cd267570de61424de306f6a6b4e14d0.tar.gz
linux-53caeaa17cd267570de61424de306f6a6b4e14d0.tar.bz2
linux-53caeaa17cd267570de61424de306f6a6b4e14d0.zip
smb: client: remove ->create_lease_buf op
Add a generic function for both create_lease v1 and v2. Signed-off-by: Enzo Matsumiya <ematsumiya@suse.de>
-rw-r--r--fs/smb/client/cifsglob.h2
-rw-r--r--fs/smb/client/smb2ops.c68
-rw-r--r--fs/smb/client/smb2pdu.c49
3 files changed, 48 insertions, 71 deletions
diff --git a/fs/smb/client/cifsglob.h b/fs/smb/client/cifsglob.h
index 0e2a532ff1ab..d1eea3ff133b 100644
--- a/fs/smb/client/cifsglob.h
+++ b/fs/smb/client/cifsglob.h
@@ -302,8 +302,6 @@ struct smb_version_operations {
struct TCP_Server_Info *server);
int (*calc_signature)(struct smb_rqst *, struct TCP_Server_Info *,
bool allocate_crypto);
- /* create lease context buffer for CREATE request */
- char * (*create_lease_buf)(u8 *lease_key, u8 oplock);
/* parse lease context buffer and return oplock/epoch info */
__u8 (*parse_lease_buf)(void *buf, unsigned int *epoch, char *lkey);
int (*duplicate_extents)(const unsigned int, struct cifsFileInfo *src,
diff --git a/fs/smb/client/smb2ops.c b/fs/smb/client/smb2ops.c
index 6018411f9cbf..78a73939094e 100644
--- a/fs/smb/client/smb2ops.c
+++ b/fs/smb/client/smb2ops.c
@@ -3990,71 +3990,6 @@ bool smb21_is_read_op(__u32 oplock)
!(oplock & SMB2_LEASE_WRITE_CACHING_HE);
}
-static __le32
-map_oplock_to_lease(u8 oplock)
-{
- if (oplock == SMB2_OPLOCK_LEVEL_EXCLUSIVE)
- return SMB2_LEASE_WRITE_CACHING_LE | SMB2_LEASE_READ_CACHING_LE;
- else if (oplock == SMB2_OPLOCK_LEVEL_II)
- return SMB2_LEASE_READ_CACHING_LE;
- else if (oplock == SMB2_OPLOCK_LEVEL_BATCH)
- return SMB2_LEASE_HANDLE_CACHING_LE | SMB2_LEASE_READ_CACHING_LE |
- SMB2_LEASE_WRITE_CACHING_LE;
- return 0;
-}
-
-static char *
-smb2_create_lease_buf(u8 *lease_key, u8 oplock)
-{
- struct create_lease *buf;
-
- buf = kzalloc(sizeof(struct create_lease), GFP_KERNEL);
- if (!buf)
- return NULL;
-
- memcpy(&buf->lcontext.LeaseKey, lease_key, SMB2_LEASE_KEY_SIZE);
- buf->lcontext.LeaseState = map_oplock_to_lease(oplock);
-
- buf->ccontext.DataOffset = cpu_to_le16(offsetof
- (struct create_lease, lcontext));
- buf->ccontext.DataLength = cpu_to_le32(sizeof(struct lease_context));
- buf->ccontext.NameOffset = cpu_to_le16(offsetof
- (struct create_lease, Name));
- buf->ccontext.NameLength = cpu_to_le16(4);
- /* SMB2_CREATE_REQUEST_LEASE is "RqLs" */
- buf->Name[0] = 'R';
- buf->Name[1] = 'q';
- buf->Name[2] = 'L';
- buf->Name[3] = 's';
- return (char *)buf;
-}
-
-static char *
-smb3_create_lease_buf(u8 *lease_key, u8 oplock)
-{
- struct create_lease_v2 *buf;
-
- buf = kzalloc(sizeof(struct create_lease_v2), GFP_KERNEL);
- if (!buf)
- return NULL;
-
- memcpy(&buf->lcontext.LeaseKey, lease_key, SMB2_LEASE_KEY_SIZE);
- buf->lcontext.LeaseState = map_oplock_to_lease(oplock);
-
- buf->ccontext.DataOffset = cpu_to_le16(offsetof
- (struct create_lease_v2, lcontext));
- buf->ccontext.DataLength = cpu_to_le32(sizeof(struct lease_context_v2));
- buf->ccontext.NameOffset = cpu_to_le16(offsetof
- (struct create_lease_v2, Name));
- buf->ccontext.NameLength = cpu_to_le16(4);
- /* SMB2_CREATE_REQUEST_LEASE is "RqLs" */
- buf->Name[0] = 'R';
- buf->Name[1] = 'q';
- buf->Name[2] = 'L';
- buf->Name[3] = 's';
- return (char *)buf;
-}
-
static __u8
smb2_parse_lease_buf(void *buf, unsigned int *epoch, char *lease_key)
{
@@ -5091,7 +5026,6 @@ struct smb_version_operations smb21_operations = {
.qfs_tcon = smb2_qfs_tcon,
.queryfs = smb2_queryfs,
.calc_signature = smb2_calc_signature,
- .create_lease_buf = smb2_create_lease_buf,
.parse_lease_buf = smb2_parse_lease_buf,
};
@@ -5106,7 +5040,6 @@ struct smb_version_operations smb30_operations = {
.queryfs = smb2_queryfs,
.generate_signingkey = generate_smb30signingkey,
.calc_signature = smb3_calc_signature,
- .create_lease_buf = smb3_create_lease_buf,
.parse_lease_buf = smb3_parse_lease_buf,
.duplicate_extents = smb2_duplicate_extents,
.fallocate = smb3_fallocate,
@@ -5126,7 +5059,6 @@ struct smb_version_operations smb311_operations = {
.queryfs = smb311_queryfs,
.generate_signingkey = generate_smb311signingkey,
.calc_signature = smb3_calc_signature,
- .create_lease_buf = smb3_create_lease_buf,
.parse_lease_buf = smb3_parse_lease_buf,
.duplicate_extents = smb2_duplicate_extents,
.fallocate = smb3_fallocate,
diff --git a/fs/smb/client/smb2pdu.c b/fs/smb/client/smb2pdu.c
index 17634cdd60ba..9ed77efb9b62 100644
--- a/fs/smb/client/smb2pdu.c
+++ b/fs/smb/client/smb2pdu.c
@@ -2384,6 +2384,53 @@ int smb2_parse_contexts(struct TCP_Server_Info *server,
return 0;
}
+static __le32 map_oplock_to_lease(u8 oplock)
+{
+ if (oplock == SMB2_OPLOCK_LEVEL_EXCLUSIVE)
+ return SMB2_LEASE_WRITE_CACHING_LE | SMB2_LEASE_READ_CACHING_LE;
+
+ if (oplock == SMB2_OPLOCK_LEVEL_II)
+ return SMB2_LEASE_READ_CACHING_LE;
+
+ if (oplock == SMB2_OPLOCK_LEVEL_BATCH)
+ return SMB2_LEASE_HANDLE_CACHING_LE | SMB2_LEASE_READ_CACHING_LE |
+ SMB2_LEASE_WRITE_CACHING_LE;
+ return 0;
+}
+
+/*
+ * The only difference between create_lease v1 and v2 is a 4-byte padding at the end of v2, so we
+ * can allocate/initialize one based only in struct create_lease (members offsets are equal too).
+ */
+static void *create_lease_buf(u8 *lease_key, u8 oplock, u16 protocol_id)
+{
+ struct create_lease *buf;
+ u32 len = sizeof(struct lease_context);
+
+ buf = kzalloc(len, GFP_KERNEL);
+ if (!buf)
+ return NULL;
+
+ if (protocol_id >= SMB30_PROT_ID)
+ len += 4;
+
+ memcpy(&buf->lcontext.LeaseKey, lease_key, SMB2_LEASE_KEY_SIZE);
+ buf->lcontext.LeaseState = map_oplock_to_lease(oplock);
+
+ buf->ccontext.DataOffset = cpu_to_le16(offsetof(struct create_lease, lcontext));
+ buf->ccontext.DataLength = cpu_to_le32(len);
+ buf->ccontext.NameOffset = cpu_to_le16(offsetof(struct create_lease, Name));
+ buf->ccontext.NameLength = cpu_to_le16(4);
+
+ /* SMB2_CREATE_REQUEST_LEASE is "RqLs" */
+ buf->Name[0] = 'R';
+ buf->Name[1] = 'q';
+ buf->Name[2] = 'L';
+ buf->Name[3] = 's';
+
+ return buf;
+}
+
static int
add_lease_context(struct TCP_Server_Info *server,
struct smb2_create_req *req,
@@ -2392,7 +2439,7 @@ add_lease_context(struct TCP_Server_Info *server,
{
unsigned int num = *num_iovec;
- iov[num].iov_base = server->ops->create_lease_buf(lease_key, *oplock);
+ iov[num].iov_base = create_lease_buf(lease_key, *oplock, server->vals->protocol_id);
if (iov[num].iov_base == NULL)
return -ENOMEM;
iov[num].iov_len = server->vals->create_lease_size;