aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/crypto/qat/qat_common/adf_sysfs.c
diff options
context:
space:
mode:
authorGiovanni Cabiddu <giovanni.cabiddu@intel.com>2022-06-27 09:36:49 +0100
committerHerbert Xu <herbert@gondor.apana.org.au>2022-07-08 15:15:59 +0800
commit5ee52118ac1481dd8a8f7e6a9bfe6ee05ac6ec92 (patch)
tree4fe54c5090c0414477cf296154ee7a13c812892f /drivers/crypto/qat/qat_common/adf_sysfs.c
parentcrypto: arm64/gcm - Select AEAD for GHASH_ARM64_CE (diff)
downloadlinux-dev-5ee52118ac1481dd8a8f7e6a9bfe6ee05ac6ec92.tar.xz
linux-dev-5ee52118ac1481dd8a8f7e6a9bfe6ee05ac6ec92.zip
crypto: qat - expose device state through sysfs for 4xxx
Expose the device state through an attribute in sysfs and allow to change it. This is to stop and shutdown a QAT device in order to change its configuration. The state attribute has been added to a newly created `qat` attribute group which will contain all _QAT specific_ attributes. The logic that implements the sysfs entries is part of a new file, adf_sysfs.c. This exposes an entry point to allow the driver to create attributes. The function that creates the sysfs attributes is called from the probe function of the driver and not in the state machine init function to allow the change of states even if the device is in the down state. In order to restore the device configuration between a transition from down to up, the function that configures the devices has been abstracted into the HW data structure. The `state` attribute is only exposed for qat_4xxx devices. Signed-off-by: Giovanni Cabiddu <giovanni.cabiddu@intel.com> Co-developed-by: Tomasz Kowallik <tomaszx.kowalik@intel.com> Signed-off-by: Tomasz Kowallik <tomaszx.kowalik@intel.com> Reviewed-by: Adam Guerin <adam.guerin@intel.com> Reviewed-by: Fiona Trahe <fiona.trahe@intel.com> Reviewed-by: Wojciech Ziemba <wojciech.ziemba@intel.com> Reviewed-by: Vladis Dronov <vdronov@redhat.com> Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>
Diffstat (limited to '')
-rw-r--r--drivers/crypto/qat/qat_common/adf_sysfs.c119
1 files changed, 119 insertions, 0 deletions
diff --git a/drivers/crypto/qat/qat_common/adf_sysfs.c b/drivers/crypto/qat/qat_common/adf_sysfs.c
new file mode 100644
index 000000000000..8f47a5694dd7
--- /dev/null
+++ b/drivers/crypto/qat/qat_common/adf_sysfs.c
@@ -0,0 +1,119 @@
+// SPDX-License-Identifier: (BSD-3-Clause OR GPL-2.0-only)
+/* Copyright(c) 2022 Intel Corporation */
+#include <linux/device.h>
+#include <linux/errno.h>
+#include <linux/pci.h>
+#include "adf_accel_devices.h"
+#include "adf_cfg.h"
+#include "adf_common_drv.h"
+
+static const char * const state_operations[] = {
+ [DEV_DOWN] = "down",
+ [DEV_UP] = "up",
+};
+
+static ssize_t state_show(struct device *dev, struct device_attribute *attr,
+ char *buf)
+{
+ struct adf_accel_dev *accel_dev;
+ char *state;
+
+ accel_dev = adf_devmgr_pci_to_accel_dev(to_pci_dev(dev));
+ if (!accel_dev)
+ return -EINVAL;
+
+ state = adf_dev_started(accel_dev) ? "up" : "down";
+ return sysfs_emit(buf, "%s\n", state);
+}
+
+static ssize_t state_store(struct device *dev, struct device_attribute *attr,
+ const char *buf, size_t count)
+{
+ struct adf_accel_dev *accel_dev;
+ u32 accel_id;
+ int ret;
+
+ accel_dev = adf_devmgr_pci_to_accel_dev(to_pci_dev(dev));
+ if (!accel_dev)
+ return -EINVAL;
+
+ accel_id = accel_dev->accel_id;
+
+ if (adf_devmgr_in_reset(accel_dev) || adf_dev_in_use(accel_dev)) {
+ dev_info(dev, "Device qat_dev%d is busy\n", accel_id);
+ return -EBUSY;
+ }
+
+ ret = sysfs_match_string(state_operations, buf);
+ if (ret < 0)
+ return ret;
+
+ switch (ret) {
+ case DEV_DOWN:
+ if (!adf_dev_started(accel_dev)) {
+ dev_info(dev, "Device qat_dev%d already down\n",
+ accel_id);
+ return -EINVAL;
+ }
+
+ dev_info(dev, "Stopping device qat_dev%d\n", accel_id);
+
+ adf_dev_stop(accel_dev);
+ adf_dev_shutdown(accel_dev);
+
+ break;
+ case DEV_UP:
+ if (adf_dev_started(accel_dev)) {
+ dev_info(dev, "Device qat_dev%d already up\n",
+ accel_id);
+ return -EINVAL;
+ }
+
+ dev_info(dev, "Starting device qat_dev%d\n", accel_id);
+
+ ret = GET_HW_DATA(accel_dev)->dev_config(accel_dev);
+ if (!ret)
+ ret = adf_dev_init(accel_dev);
+ if (!ret)
+ ret = adf_dev_start(accel_dev);
+
+ if (ret < 0) {
+ dev_err(dev, "Failed to start device qat_dev%d\n",
+ accel_id);
+ adf_dev_stop(accel_dev);
+ adf_dev_shutdown(accel_dev);
+ return ret;
+ }
+ break;
+ default:
+ return -EINVAL;
+ }
+
+ return count;
+}
+
+static DEVICE_ATTR_RW(state);
+
+static struct attribute *qat_attrs[] = {
+ &dev_attr_state.attr,
+ NULL,
+};
+
+static struct attribute_group qat_group = {
+ .attrs = qat_attrs,
+ .name = "qat",
+};
+
+int adf_sysfs_init(struct adf_accel_dev *accel_dev)
+{
+ int ret;
+
+ ret = devm_device_add_group(&GET_DEV(accel_dev), &qat_group);
+ if (ret) {
+ dev_err(&GET_DEV(accel_dev),
+ "Failed to create qat attribute group: %d\n", ret);
+ }
+
+ return ret;
+}
+EXPORT_SYMBOL_GPL(adf_sysfs_init);