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

bpf: Move bpf_get_file_xattr to fs/bpf_fs_kfuncs.c

We are putting all fs kfuncs in fs/bpf_fs_kfuncs.c. Move existing
bpf_get_file_xattr to it.

Signed-off-by: Song Liu <song@kernel.org>
Link: https://lore.kernel.org/r/20240806230904.71194-2-song@kernel.org
Signed-off-by: Alexei Starovoitov <ast@kernel.org>

authored by

Song Liu and committed by
Alexei Starovoitov
fa4e5afa 6e083ab0

+38 -68
+38
fs/bpf_fs_kfuncs.c
··· 8 8 #include <linux/fs.h> 9 9 #include <linux/file.h> 10 10 #include <linux/mm.h> 11 + #include <linux/xattr.h> 11 12 12 13 __bpf_kfunc_start_defs(); 13 14 ··· 93 92 return len; 94 93 } 95 94 95 + /** 96 + * bpf_get_file_xattr - get xattr of a file 97 + * @file: file to get xattr from 98 + * @name__str: name of the xattr 99 + * @value_p: output buffer of the xattr value 100 + * 101 + * Get xattr *name__str* of *file* and store the output in *value_ptr*. 102 + * 103 + * For security reasons, only *name__str* with prefix "user." is allowed. 104 + * 105 + * Return: 0 on success, a negative value on error. 106 + */ 107 + __bpf_kfunc int bpf_get_file_xattr(struct file *file, const char *name__str, 108 + struct bpf_dynptr *value_p) 109 + { 110 + struct bpf_dynptr_kern *value_ptr = (struct bpf_dynptr_kern *)value_p; 111 + struct dentry *dentry; 112 + u32 value_len; 113 + void *value; 114 + int ret; 115 + 116 + if (strncmp(name__str, XATTR_USER_PREFIX, XATTR_USER_PREFIX_LEN)) 117 + return -EPERM; 118 + 119 + value_len = __bpf_dynptr_size(value_ptr); 120 + value = __bpf_dynptr_data_rw(value_ptr, value_len); 121 + if (!value) 122 + return -EINVAL; 123 + 124 + dentry = file_dentry(file); 125 + ret = inode_permission(&nop_mnt_idmap, dentry->d_inode, MAY_READ); 126 + if (ret) 127 + return ret; 128 + return __vfs_getxattr(dentry, dentry->d_inode, name__str, value, value_len); 129 + } 130 + 96 131 __bpf_kfunc_end_defs(); 97 132 98 133 BTF_KFUNCS_START(bpf_fs_kfunc_set_ids) ··· 136 99 KF_ACQUIRE | KF_TRUSTED_ARGS | KF_RET_NULL) 137 100 BTF_ID_FLAGS(func, bpf_put_file, KF_RELEASE) 138 101 BTF_ID_FLAGS(func, bpf_path_d_path, KF_TRUSTED_ARGS) 102 + BTF_ID_FLAGS(func, bpf_get_file_xattr, KF_SLEEPABLE | KF_TRUSTED_ARGS) 139 103 BTF_KFUNCS_END(bpf_fs_kfunc_set_ids) 140 104 141 105 static int bpf_fs_kfuncs_filter(const struct bpf_prog *prog, u32 kfunc_id)
-68
kernel/trace/bpf_trace.c
··· 24 24 #include <linux/key.h> 25 25 #include <linux/verification.h> 26 26 #include <linux/namei.h> 27 - #include <linux/fileattr.h> 28 27 29 28 #include <net/bpf_sk_storage.h> 30 29 ··· 1437 1438 1438 1439 late_initcall(bpf_key_sig_kfuncs_init); 1439 1440 #endif /* CONFIG_KEYS */ 1440 - 1441 - /* filesystem kfuncs */ 1442 - __bpf_kfunc_start_defs(); 1443 - 1444 - /** 1445 - * bpf_get_file_xattr - get xattr of a file 1446 - * @file: file to get xattr from 1447 - * @name__str: name of the xattr 1448 - * @value_p: output buffer of the xattr value 1449 - * 1450 - * Get xattr *name__str* of *file* and store the output in *value_ptr*. 1451 - * 1452 - * For security reasons, only *name__str* with prefix "user." is allowed. 1453 - * 1454 - * Return: 0 on success, a negative value on error. 1455 - */ 1456 - __bpf_kfunc int bpf_get_file_xattr(struct file *file, const char *name__str, 1457 - struct bpf_dynptr *value_p) 1458 - { 1459 - struct bpf_dynptr_kern *value_ptr = (struct bpf_dynptr_kern *)value_p; 1460 - struct dentry *dentry; 1461 - u32 value_len; 1462 - void *value; 1463 - int ret; 1464 - 1465 - if (strncmp(name__str, XATTR_USER_PREFIX, XATTR_USER_PREFIX_LEN)) 1466 - return -EPERM; 1467 - 1468 - value_len = __bpf_dynptr_size(value_ptr); 1469 - value = __bpf_dynptr_data_rw(value_ptr, value_len); 1470 - if (!value) 1471 - return -EINVAL; 1472 - 1473 - dentry = file_dentry(file); 1474 - ret = inode_permission(&nop_mnt_idmap, dentry->d_inode, MAY_READ); 1475 - if (ret) 1476 - return ret; 1477 - return __vfs_getxattr(dentry, dentry->d_inode, name__str, value, value_len); 1478 - } 1479 - 1480 - __bpf_kfunc_end_defs(); 1481 - 1482 - BTF_KFUNCS_START(fs_kfunc_set_ids) 1483 - BTF_ID_FLAGS(func, bpf_get_file_xattr, KF_SLEEPABLE | KF_TRUSTED_ARGS) 1484 - BTF_KFUNCS_END(fs_kfunc_set_ids) 1485 - 1486 - static int bpf_get_file_xattr_filter(const struct bpf_prog *prog, u32 kfunc_id) 1487 - { 1488 - if (!btf_id_set8_contains(&fs_kfunc_set_ids, kfunc_id)) 1489 - return 0; 1490 - 1491 - /* Only allow to attach from LSM hooks, to avoid recursion */ 1492 - return prog->type != BPF_PROG_TYPE_LSM ? -EACCES : 0; 1493 - } 1494 - 1495 - static const struct btf_kfunc_id_set bpf_fs_kfunc_set = { 1496 - .owner = THIS_MODULE, 1497 - .set = &fs_kfunc_set_ids, 1498 - .filter = bpf_get_file_xattr_filter, 1499 - }; 1500 - 1501 - static int __init bpf_fs_kfuncs_init(void) 1502 - { 1503 - return register_btf_kfunc_id_set(BPF_PROG_TYPE_LSM, &bpf_fs_kfunc_set); 1504 - } 1505 - 1506 - late_initcall(bpf_fs_kfuncs_init); 1507 1441 1508 1442 static const struct bpf_func_proto * 1509 1443 bpf_tracing_func_proto(enum bpf_func_id func_id, const struct bpf_prog *prog)