Skip to content

Commit b914875

Browse files
Paulo AlcantaraSteve French
authored andcommitted
smb: client: reduce stack usage in smb2_query_info_compound()
Clang warns about exceeded stack frame size fs/smb/client/smb2ops.c:2521:1: warning: stack frame size (1336) exceeds limit (1024) in 'smb2_query_info_compound' [-Wframe-larger-than] Fix this by allocating a structure that will hold most of the large variables. Signed-off-by: Paulo Alcantara (SUSE) <[email protected]> Signed-off-by: Steve French <[email protected]>
1 parent f4e5ceb commit b914875

File tree

1 file changed

+16
-14
lines changed

1 file changed

+16
-14
lines changed

fs/smb/client/smb2ops.c

Lines changed: 16 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -2513,15 +2513,13 @@ smb2_query_info_compound(const unsigned int xid, struct cifs_tcon *tcon,
25132513
struct kvec *rsp, int *buftype,
25142514
struct cifs_sb_info *cifs_sb)
25152515
{
2516+
struct smb2_compound_vars *vars;
25162517
struct cifs_ses *ses = tcon->ses;
25172518
struct TCP_Server_Info *server = cifs_pick_channel(ses);
25182519
int flags = CIFS_CP_CREATE_CLOSE_OP;
2519-
struct smb_rqst rqst[3];
2520+
struct smb_rqst *rqst;
25202521
int resp_buftype[3];
2521-
struct kvec rsp_iov[3];
2522-
struct kvec open_iov[SMB2_CREATE_IOV_SIZE];
2523-
struct kvec qi_iov[1];
2524-
struct kvec close_iov[1];
2522+
struct kvec *rsp_iov;
25252523
u8 oplock = SMB2_OPLOCK_LEVEL_NONE;
25262524
struct cifs_open_parms oparms;
25272525
struct cifs_fid fid;
@@ -2538,9 +2536,14 @@ smb2_query_info_compound(const unsigned int xid, struct cifs_tcon *tcon,
25382536
if (smb3_encryption_required(tcon))
25392537
flags |= CIFS_TRANSFORM_REQ;
25402538

2541-
memset(rqst, 0, sizeof(rqst));
25422539
resp_buftype[0] = resp_buftype[1] = resp_buftype[2] = CIFS_NO_BUFFER;
2543-
memset(rsp_iov, 0, sizeof(rsp_iov));
2540+
vars = kzalloc(sizeof(*vars), GFP_KERNEL);
2541+
if (!vars) {
2542+
rc = -ENOMEM;
2543+
goto out_free_path;
2544+
}
2545+
rqst = vars->rqst;
2546+
rsp_iov = vars->rsp_iov;
25442547

25452548
/*
25462549
* We can only call this for things we know are directories.
@@ -2549,8 +2552,7 @@ smb2_query_info_compound(const unsigned int xid, struct cifs_tcon *tcon,
25492552
open_cached_dir(xid, tcon, path, cifs_sb, false,
25502553
&cfid); /* cfid null if open dir failed */
25512554

2552-
memset(&open_iov, 0, sizeof(open_iov));
2553-
rqst[0].rq_iov = open_iov;
2555+
rqst[0].rq_iov = vars->open_iov;
25542556
rqst[0].rq_nvec = SMB2_CREATE_IOV_SIZE;
25552557

25562558
oparms = (struct cifs_open_parms) {
@@ -2568,8 +2570,7 @@ smb2_query_info_compound(const unsigned int xid, struct cifs_tcon *tcon,
25682570
goto qic_exit;
25692571
smb2_set_next_command(tcon, &rqst[0]);
25702572

2571-
memset(&qi_iov, 0, sizeof(qi_iov));
2572-
rqst[1].rq_iov = qi_iov;
2573+
rqst[1].rq_iov = &vars->qi_iov;
25732574
rqst[1].rq_nvec = 1;
25742575

25752576
if (cfid) {
@@ -2596,8 +2597,7 @@ smb2_query_info_compound(const unsigned int xid, struct cifs_tcon *tcon,
25962597
smb2_set_related(&rqst[1]);
25972598
}
25982599

2599-
memset(&close_iov, 0, sizeof(close_iov));
2600-
rqst[2].rq_iov = close_iov;
2600+
rqst[2].rq_iov = &vars->close_iov;
26012601
rqst[2].rq_nvec = 1;
26022602

26032603
rc = SMB2_close_init(tcon, server,
@@ -2628,14 +2628,16 @@ smb2_query_info_compound(const unsigned int xid, struct cifs_tcon *tcon,
26282628
*buftype = resp_buftype[1];
26292629

26302630
qic_exit:
2631-
kfree(utf16_path);
26322631
SMB2_open_free(&rqst[0]);
26332632
SMB2_query_info_free(&rqst[1]);
26342633
SMB2_close_free(&rqst[2]);
26352634
free_rsp_buf(resp_buftype[0], rsp_iov[0].iov_base);
26362635
free_rsp_buf(resp_buftype[2], rsp_iov[2].iov_base);
26372636
if (cfid)
26382637
close_cached_dir(cfid);
2638+
kfree(vars);
2639+
out_free_path:
2640+
kfree(utf16_path);
26392641
return rc;
26402642
}
26412643

0 commit comments

Comments
 (0)