Skip to content

Commit d32f79a

Browse files
committed
landlock: Use scoped guards for ruleset
Simplify error handling by replacing goto statements with automatic calls to landlock_put_ruleset() when going out of scope. This change will be easy to backport to v6.6 if needed, only the kernel.h include line conflicts. As for any other similar changes, we should be careful when backporting without goto statements. Add missing include file. Reviewed-by: Günther Noack <[email protected]> Link: https://lore.kernel.org/r/[email protected] Signed-off-by: Mickaël Salaün <[email protected]>
1 parent 25ccc75 commit d32f79a

File tree

3 files changed

+23
-29
lines changed

3 files changed

+23
-29
lines changed

security/landlock/ruleset.c

Lines changed: 10 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -8,11 +8,13 @@
88

99
#include <linux/bits.h>
1010
#include <linux/bug.h>
11+
#include <linux/cleanup.h>
1112
#include <linux/compiler_types.h>
1213
#include <linux/err.h>
1314
#include <linux/errno.h>
1415
#include <linux/kernel.h>
1516
#include <linux/lockdep.h>
17+
#include <linux/mutex.h>
1618
#include <linux/overflow.h>
1719
#include <linux/rbtree.h>
1820
#include <linux/refcount.h>
@@ -537,7 +539,7 @@ struct landlock_ruleset *
537539
landlock_merge_ruleset(struct landlock_ruleset *const parent,
538540
struct landlock_ruleset *const ruleset)
539541
{
540-
struct landlock_ruleset *new_dom;
542+
struct landlock_ruleset *new_dom __free(landlock_put_ruleset) = NULL;
541543
u32 num_layers;
542544
int err;
543545

@@ -557,29 +559,25 @@ landlock_merge_ruleset(struct landlock_ruleset *const parent,
557559
new_dom = create_ruleset(num_layers);
558560
if (IS_ERR(new_dom))
559561
return new_dom;
562+
560563
new_dom->hierarchy =
561564
kzalloc(sizeof(*new_dom->hierarchy), GFP_KERNEL_ACCOUNT);
562-
if (!new_dom->hierarchy) {
563-
err = -ENOMEM;
564-
goto out_put_dom;
565-
}
565+
if (!new_dom->hierarchy)
566+
return ERR_PTR(-ENOMEM);
567+
566568
refcount_set(&new_dom->hierarchy->usage, 1);
567569

568570
/* ...as a child of @parent... */
569571
err = inherit_ruleset(parent, new_dom);
570572
if (err)
571-
goto out_put_dom;
573+
return ERR_PTR(err);
572574

573575
/* ...and including @ruleset. */
574576
err = merge_ruleset(new_dom, ruleset);
575577
if (err)
576-
goto out_put_dom;
577-
578-
return new_dom;
578+
return ERR_PTR(err);
579579

580-
out_put_dom:
581-
landlock_put_ruleset(new_dom);
582-
return ERR_PTR(err);
580+
return no_free_ptr(new_dom);
583581
}
584582

585583
/*

security/landlock/ruleset.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,8 @@
1111

1212
#include <linux/bitops.h>
1313
#include <linux/build_bug.h>
14+
#include <linux/cleanup.h>
15+
#include <linux/err.h>
1416
#include <linux/kernel.h>
1517
#include <linux/mutex.h>
1618
#include <linux/rbtree.h>
@@ -252,6 +254,9 @@ landlock_create_ruleset(const access_mask_t access_mask_fs,
252254
void landlock_put_ruleset(struct landlock_ruleset *const ruleset);
253255
void landlock_put_ruleset_deferred(struct landlock_ruleset *const ruleset);
254256

257+
DEFINE_FREE(landlock_put_ruleset, struct landlock_ruleset *,
258+
if (!IS_ERR_OR_NULL(_T)) landlock_put_ruleset(_T))
259+
255260
int landlock_insert_rule(struct landlock_ruleset *const ruleset,
256261
const struct landlock_id id,
257262
const access_mask_t access);

security/landlock/syscalls.c

Lines changed: 8 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010
#include <linux/anon_inodes.h>
1111
#include <linux/build_bug.h>
1212
#include <linux/capability.h>
13+
#include <linux/cleanup.h>
1314
#include <linux/compiler_types.h>
1415
#include <linux/dcache.h>
1516
#include <linux/err.h>
@@ -456,10 +457,10 @@ SYSCALL_DEFINE4(landlock_add_rule, const int, ruleset_fd,
456457
SYSCALL_DEFINE2(landlock_restrict_self, const int, ruleset_fd, const __u32,
457458
flags)
458459
{
459-
struct landlock_ruleset *new_dom, *ruleset;
460+
struct landlock_ruleset *new_dom,
461+
*ruleset __free(landlock_put_ruleset) = NULL;
460462
struct cred *new_cred;
461463
struct landlock_cred_security *new_llcred;
462-
int err;
463464

464465
if (!is_initialized())
465466
return -EOPNOTSUPP;
@@ -483,10 +484,9 @@ SYSCALL_DEFINE2(landlock_restrict_self, const int, ruleset_fd, const __u32,
483484

484485
/* Prepares new credentials. */
485486
new_cred = prepare_creds();
486-
if (!new_cred) {
487-
err = -ENOMEM;
488-
goto out_put_ruleset;
489-
}
487+
if (!new_cred)
488+
return -ENOMEM;
489+
490490
new_llcred = landlock_cred(new_cred);
491491

492492
/*
@@ -495,21 +495,12 @@ SYSCALL_DEFINE2(landlock_restrict_self, const int, ruleset_fd, const __u32,
495495
*/
496496
new_dom = landlock_merge_ruleset(new_llcred->domain, ruleset);
497497
if (IS_ERR(new_dom)) {
498-
err = PTR_ERR(new_dom);
499-
goto out_put_creds;
498+
abort_creds(new_cred);
499+
return PTR_ERR(new_dom);
500500
}
501501

502502
/* Replaces the old (prepared) domain. */
503503
landlock_put_ruleset(new_llcred->domain);
504504
new_llcred->domain = new_dom;
505-
506-
landlock_put_ruleset(ruleset);
507505
return commit_creds(new_cred);
508-
509-
out_put_creds:
510-
abort_creds(new_cred);
511-
512-
out_put_ruleset:
513-
landlock_put_ruleset(ruleset);
514-
return err;
515506
}

0 commit comments

Comments
 (0)