Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

lsm: replace the name field with a pointer to the lsm_id struct

Reduce the duplication between the lsm_id struct and the DEFINE_LSM()
definition by linking the lsm_id struct directly into the individual
LSM's DEFINE_LSM() instance.

Linking the lsm_id into the LSM definition also allows us to simplify
the security_add_hooks() function by removing the code which populates
the lsm_idlist[] array and moving it into the normal LSM startup code
where the LSM list is parsed and the individual LSMs are enabled,
making for a cleaner implementation with less overhead at boot.

Reviewed-by: Kees Cook <kees@kernel.org>
Reviewed-by: John Johansen <john.johansen@canonical.com>
Reviewed-by: Casey Schaufler <casey@schaufler-ca.com>
Reviewed-by: Mimi Zohar <zohar@linux.ibm.com>
Signed-off-by: Paul Moore <paul@paul-moore.com>

+33 -42
+1 -1
include/linux/lsm_hooks.h
··· 152 152 }; 153 153 154 154 struct lsm_info { 155 - const char *name; /* Required. */ 155 + const struct lsm_id *id; 156 156 enum lsm_order order; /* Optional: default is LSM_ORDER_MUTABLE */ 157 157 unsigned long flags; /* Optional: flags describing LSM */ 158 158 int *enabled; /* Optional: controlled by CONFIG_LSM */
+1 -1
security/apparmor/lsm.c
··· 2555 2555 } 2556 2556 2557 2557 DEFINE_LSM(apparmor) = { 2558 - .name = "apparmor", 2558 + .id = &apparmor_lsmid, 2559 2559 .flags = LSM_FLAG_LEGACY_MAJOR | LSM_FLAG_EXCLUSIVE, 2560 2560 .enabled = &apparmor_enabled, 2561 2561 .blobs = &apparmor_blob_sizes,
+1 -1
security/bpf/hooks.c
··· 33 33 }; 34 34 35 35 DEFINE_LSM(bpf) = { 36 - .name = "bpf", 36 + .id = &bpf_lsmid, 37 37 .init = bpf_lsm_init, 38 38 .blobs = &bpf_lsm_blob_sizes 39 39 };
+1 -1
security/commoncap.c
··· 1505 1505 } 1506 1506 1507 1507 DEFINE_LSM(capability) = { 1508 - .name = "capability", 1508 + .id = &capability_lsmid, 1509 1509 .order = LSM_ORDER_FIRST, 1510 1510 .init = capability_init, 1511 1511 };
+1 -1
security/integrity/evm/evm_main.c
··· 1175 1175 }; 1176 1176 1177 1177 DEFINE_LSM(evm) = { 1178 - .name = "evm", 1178 + .id = &evm_lsmid, 1179 1179 .init = init_evm_lsm, 1180 1180 .order = LSM_ORDER_LAST, 1181 1181 .blobs = &evm_blob_sizes,
+1 -1
security/integrity/ima/ima_main.c
··· 1279 1279 }; 1280 1280 1281 1281 DEFINE_LSM(ima) = { 1282 - .name = "ima", 1282 + .id = &ima_lsmid, 1283 1283 .init = init_ima_lsm, 1284 1284 .order = LSM_ORDER_LAST, 1285 1285 .blobs = &ima_blob_sizes,
+1 -1
security/ipe/ipe.c
··· 92 92 } 93 93 94 94 DEFINE_LSM(ipe) = { 95 - .name = "ipe", 95 + .id = &ipe_lsmid, 96 96 .init = ipe_init, 97 97 .blobs = &ipe_blobs, 98 98 };
+1 -1
security/landlock/setup.c
··· 75 75 } 76 76 77 77 DEFINE_LSM(LANDLOCK_NAME) = { 78 - .name = LANDLOCK_NAME, 78 + .id = &landlock_lsmid, 79 79 .init = landlock_init, 80 80 .blobs = &landlock_blob_sizes, 81 81 };
+1 -1
security/loadpin/loadpin.c
··· 271 271 } 272 272 273 273 DEFINE_LSM(loadpin) = { 274 - .name = "loadpin", 274 + .id = &loadpin_lsmid, 275 275 .init = loadpin_init, 276 276 }; 277 277
+1 -1
security/lockdown/lockdown.c
··· 168 168 #else 169 169 DEFINE_LSM(lockdown) = { 170 170 #endif 171 - .name = "lockdown", 171 + .id = &lockdown_lsmid, 172 172 .init = lockdown_lsm_init, 173 173 };
+18 -27
security/lsm_init.c
··· 127 127 /* Enable this LSM, if it is not already set. */ 128 128 if (!lsm->enabled) 129 129 lsm->enabled = &lsm_enabled_true; 130 - ordered_lsms[last_lsm++] = lsm; 130 + ordered_lsms[last_lsm] = lsm; 131 + lsm_idlist[last_lsm++] = lsm->id; 131 132 132 - init_debug("%s ordered: %s (%s)\n", from, lsm->name, 133 + init_debug("%s ordered: %s (%s)\n", from, lsm->id->name, 133 134 is_enabled(lsm) ? "enabled" : "disabled"); 134 135 } 135 136 ··· 158 157 set_enabled(lsm, false); 159 158 return; 160 159 } else if ((lsm->flags & LSM_FLAG_EXCLUSIVE) && exclusive) { 161 - init_debug("exclusive disabled: %s\n", lsm->name); 160 + init_debug("exclusive disabled: %s\n", lsm->id->name); 162 161 set_enabled(lsm, false); 163 162 return; 164 163 } ··· 166 165 /* Mark the LSM as enabled. */ 167 166 set_enabled(lsm, true); 168 167 if ((lsm->flags & LSM_FLAG_EXCLUSIVE) && !exclusive) { 169 - init_debug("exclusive chosen: %s\n", lsm->name); 168 + init_debug("exclusive chosen: %s\n", lsm->id->name); 170 169 exclusive = lsm; 171 170 } 172 171 ··· 201 200 if (is_enabled(lsm)) { 202 201 int ret; 203 202 204 - init_debug("initializing %s\n", lsm->name); 203 + init_debug("initializing %s\n", lsm->id->name); 205 204 ret = lsm->init(); 206 - WARN(ret, "%s failed to initialize: %d\n", lsm->name, ret); 205 + WARN(ret, "%s failed to initialize: %d\n", lsm->id->name, ret); 207 206 } 208 207 } 209 208 ··· 237 236 */ 238 237 lsm_for_each_raw(major) { 239 238 if ((major->flags & LSM_FLAG_LEGACY_MAJOR) && 240 - strcmp(major->name, chosen_major_lsm) != 0) { 239 + strcmp(major->id->name, chosen_major_lsm) != 0) { 241 240 set_enabled(major, false); 242 241 init_debug("security=%s disabled: %s (only one legacy major LSM)\n", 243 - chosen_major_lsm, major->name); 242 + chosen_major_lsm, major->id->name); 244 243 } 245 244 } 246 245 } ··· 252 251 bool found = false; 253 252 254 253 lsm_for_each_raw(lsm) { 255 - if (strcmp(lsm->name, name) == 0) { 254 + if (strcmp(lsm->id->name, name) == 0) { 256 255 if (lsm->order == LSM_ORDER_MUTABLE) 257 256 append_ordered_lsm(lsm, origin); 258 257 found = true; ··· 269 268 lsm_for_each_raw(lsm) { 270 269 if (exists_ordered_lsm(lsm)) 271 270 continue; 272 - if (strcmp(lsm->name, chosen_major_lsm) == 0) 271 + if (strcmp(lsm->id->name, chosen_major_lsm) == 0) 273 272 append_ordered_lsm(lsm, "security="); 274 273 } 275 274 } ··· 286 285 continue; 287 286 set_enabled(lsm, false); 288 287 init_debug("%s skipped: %s (not in requested order)\n", 289 - origin, lsm->name); 288 + origin, lsm->id->name); 290 289 } 291 290 292 291 kfree(sep); ··· 318 317 pr_info("initializing lsm="); 319 318 lsm_early_for_each_raw(early) { 320 319 if (is_enabled(early)) 321 - pr_cont("%s%s", first++ == 0 ? "" : ",", early->name); 320 + pr_cont("%s%s", 321 + first++ == 0 ? "" : ",", early->id->name); 322 322 } 323 323 lsm_order_for_each(lsm) { 324 324 if (is_enabled(*lsm)) 325 - pr_cont("%s%s", first++ == 0 ? "" : ",", (*lsm)->name); 325 + pr_cont("%s%s", 326 + first++ == 0 ? "" : ",", (*lsm)->id->name); 326 327 } 327 328 pr_cont("\n"); 328 329 ··· 435 432 { 436 433 int i; 437 434 438 - /* 439 - * A security module may call security_add_hooks() more 440 - * than once during initialization, and LSM initialization 441 - * is serialized. Landlock is one such case. 442 - * Look at the previous entry, if there is one, for duplication. 443 - */ 444 - if (lsm_active_cnt == 0 || lsm_idlist[lsm_active_cnt - 1] != lsmid) { 445 - if (lsm_active_cnt >= MAX_LSM_COUNT) 446 - panic("%s Too many LSMs registered.\n", __func__); 447 - lsm_idlist[lsm_active_cnt++] = lsmid; 448 - } 449 - 450 435 for (i = 0; i < count; i++) { 451 436 hooks[i].lsmid = lsmid; 452 437 lsm_static_call_init(&hooks[i]); ··· 482 491 * available 483 492 */ 484 493 lsm_early_for_each_raw(lsm) { 485 - init_debug(" early started: %s (%s)\n", lsm->name, 494 + init_debug(" early started: %s (%s)\n", lsm->id->name, 486 495 is_enabled(lsm) ? "enabled" : "disabled"); 487 496 if (lsm->enabled) 488 - lsm_append(lsm->name, &lsm_names); 497 + lsm_append(lsm->id->name, &lsm_names); 489 498 } 490 499 491 500 /* Load LSMs in specified order. */
+1 -1
security/safesetid/lsm.c
··· 287 287 } 288 288 289 289 DEFINE_LSM(safesetid_security_init) = { 290 + .id = &safesetid_lsmid, 290 291 .init = safesetid_security_init, 291 - .name = "safesetid", 292 292 };
+1 -1
security/selinux/hooks.c
··· 7639 7639 /* SELinux requires early initialization in order to label 7640 7640 all processes and objects when they are created. */ 7641 7641 DEFINE_LSM(selinux) = { 7642 - .name = "selinux", 7642 + .id = &selinux_lsmid, 7643 7643 .flags = LSM_FLAG_LEGACY_MAJOR | LSM_FLAG_EXCLUSIVE, 7644 7644 .enabled = &selinux_enabled_boot, 7645 7645 .blobs = &selinux_blob_sizes,
+1 -1
security/smack/smack_lsm.c
··· 5280 5280 * all processes and objects when they are created. 5281 5281 */ 5282 5282 DEFINE_LSM(smack) = { 5283 - .name = "smack", 5283 + .id = &smack_lsmid, 5284 5284 .flags = LSM_FLAG_LEGACY_MAJOR | LSM_FLAG_EXCLUSIVE, 5285 5285 .blobs = &smack_blob_sizes, 5286 5286 .init = smack_init,
+1 -1
security/tomoyo/tomoyo.c
··· 612 612 } 613 613 614 614 DEFINE_LSM(tomoyo) = { 615 - .name = "tomoyo", 615 + .id = &tomoyo_lsmid, 616 616 .enabled = &tomoyo_enabled, 617 617 .flags = LSM_FLAG_LEGACY_MAJOR, 618 618 .blobs = &tomoyo_blob_sizes,
+1 -1
security/yama/yama_lsm.c
··· 476 476 } 477 477 478 478 DEFINE_LSM(yama) = { 479 - .name = "yama", 479 + .id = &yama_lsmid, 480 480 .init = yama_init, 481 481 };