// SPDX-License-Identifier: GPL-2.0 /* * Copyright (C) 2020-2024 Microsoft Corporation. All rights reserved. */ #include <linux/fs.h> #include <linux/namei.h> #include <linux/types.h> #include <linux/dcache.h> #include <linux/security.h> #include "ipe.h" #include "policy.h" #include "eval.h" #include "fs.h" #define MAX_VERSION_SIZE … /** * ipefs_file - defines a file in securityfs. */ struct ipefs_file { … }; /** * read_pkcs7() - Read handler for "ipe/policies/$name/pkcs7". * @f: Supplies a file structure representing the securityfs node. * @data: Supplies a buffer passed to the write syscall. * @len: Supplies the length of @data. * @offset: unused. * * @data will be populated with the pkcs7 blob representing the policy * on success. If the policy is unsigned (like the boot policy), this * will return -ENOENT. * * Return: * * Length of buffer written - Success * * %-ENOENT - Policy initializing/deleted or is unsigned */ static ssize_t read_pkcs7(struct file *f, char __user *data, size_t len, loff_t *offset) { … } /** * read_policy() - Read handler for "ipe/policies/$name/policy". * @f: Supplies a file structure representing the securityfs node. * @data: Supplies a buffer passed to the write syscall. * @len: Supplies the length of @data. * @offset: unused. * * @data will be populated with the plain-text version of the policy * on success. * * Return: * * Length of buffer written - Success * * %-ENOENT - Policy initializing/deleted */ static ssize_t read_policy(struct file *f, char __user *data, size_t len, loff_t *offset) { … } /** * read_name() - Read handler for "ipe/policies/$name/name". * @f: Supplies a file structure representing the securityfs node. * @data: Supplies a buffer passed to the write syscall. * @len: Supplies the length of @data. * @offset: unused. * * @data will be populated with the policy_name attribute on success. * * Return: * * Length of buffer written - Success * * %-ENOENT - Policy initializing/deleted */ static ssize_t read_name(struct file *f, char __user *data, size_t len, loff_t *offset) { … } /** * read_version() - Read handler for "ipe/policies/$name/version". * @f: Supplies a file structure representing the securityfs node. * @data: Supplies a buffer passed to the write syscall. * @len: Supplies the length of @data. * @offset: unused. * * @data will be populated with the version string on success. * * Return: * * Length of buffer written - Success * * %-ENOENT - Policy initializing/deleted */ static ssize_t read_version(struct file *f, char __user *data, size_t len, loff_t *offset) { … } /** * setactive() - Write handler for "ipe/policies/$name/active". * @f: Supplies a file structure representing the securityfs node. * @data: Supplies a buffer passed to the write syscall. * @len: Supplies the length of @data. * @offset: unused. * * Return: * * Length of buffer written - Success * * %-EPERM - Insufficient permission * * %-EINVAL - Invalid input * * %-ENOENT - Policy initializing/deleted */ static ssize_t setactive(struct file *f, const char __user *data, size_t len, loff_t *offset) { … } /** * getactive() - Read handler for "ipe/policies/$name/active". * @f: Supplies a file structure representing the securityfs node. * @data: Supplies a buffer passed to the write syscall. * @len: Supplies the length of @data. * @offset: unused. * * @data will be populated with the 1 or 0 depending on if the * corresponding policy is active. * * Return: * * Length of buffer written - Success * * %-ENOENT - Policy initializing/deleted */ static ssize_t getactive(struct file *f, char __user *data, size_t len, loff_t *offset) { … } /** * update_policy() - Write handler for "ipe/policies/$name/update". * @f: Supplies a file structure representing the securityfs node. * @data: Supplies a buffer passed to the write syscall. * @len: Supplies the length of @data. * @offset: unused. * * On success this updates the policy represented by $name, * in-place. * * Return: Length of buffer written on success. If an error occurs, * the function will return the -errno. */ static ssize_t update_policy(struct file *f, const char __user *data, size_t len, loff_t *offset) { … } /** * delete_policy() - write handler for "ipe/policies/$name/delete". * @f: Supplies a file structure representing the securityfs node. * @data: Supplies a buffer passed to the write syscall. * @len: Supplies the length of @data. * @offset: unused. * * On success this deletes the policy represented by $name. * * Return: * * Length of buffer written - Success * * %-EPERM - Insufficient permission/deleting active policy * * %-EINVAL - Invalid input * * %-ENOENT - Policy initializing/deleted */ static ssize_t delete_policy(struct file *f, const char __user *data, size_t len, loff_t *offset) { … } static const struct file_operations content_fops = …; static const struct file_operations pkcs7_fops = …; static const struct file_operations name_fops = …; static const struct file_operations ver_fops = …; static const struct file_operations active_fops = …; static const struct file_operations update_fops = …; static const struct file_operations delete_fops = …; /** * policy_subdir - files under a policy subdirectory */ static const struct ipefs_file policy_subdir[] = …; /** * ipe_del_policyfs_node() - Delete a securityfs entry for @p. * @p: Supplies a pointer to the policy to delete a securityfs entry for. */ void ipe_del_policyfs_node(struct ipe_policy *p) { … } /** * ipe_new_policyfs_node() - Create a securityfs entry for @p. * @p: Supplies a pointer to the policy to create a securityfs entry for. * * Return: %0 on success. If an error occurs, the function will return * the -errno. */ int ipe_new_policyfs_node(struct ipe_policy *p) { … }