Commit fd77d8da authored by Damian Muszynski's avatar Damian Muszynski Committed by Herbert Xu
Browse files

crypto: qat - add internal timer for qat 4xxx



The power management feature in QAT 4xxx devices can disable clock
sources used to implement timers. Because of that, the firmware needs to
get an external reliable source of time.

Add a kernel delayed work that periodically sends an event to the
firmware. This is triggered every 200ms. At each execution, the driver
sends a sync request to the firmware reporting the current timestamp
counter value.

This is a pre-requisite for enabling the heartbeat, telemetry and
rate limiting features.

Signed-off-by: default avatarDamian Muszynski <damian.muszynski@intel.com>
Reviewed-by: default avatarGiovanni Cabiddu <giovanni.cabiddu@intel.com>
Reviewed-by: default avatarAndy Shevchenko <andriy.shevchenko@linux.intel.com>
Signed-off-by: default avatarHerbert Xu <herbert@gondor.apana.org.au>
parent 865b50fe
Loading
Loading
Loading
Loading
+3 −0
Original line number Diff line number Diff line
@@ -8,6 +8,7 @@
#include <adf_gen4_hw_data.h>
#include <adf_gen4_pfvf.h>
#include <adf_gen4_pm.h>
#include <adf_gen4_timer.h>
#include "adf_4xxx_hw_data.h"
#include "icp_qat_hw.h"

@@ -508,6 +509,8 @@ void adf_init_hw_data_4xxx(struct adf_hw_device_data *hw_data, u32 dev_id)
	hw_data->enable_pm = adf_gen4_enable_pm;
	hw_data->handle_pm_interrupt = adf_gen4_handle_pm_interrupt;
	hw_data->dev_config = adf_gen4_dev_config;
	hw_data->start_timer = adf_gen4_timer_start;
	hw_data->stop_timer = adf_gen4_timer_stop;

	adf_gen4_init_hw_csr_ops(&hw_data->csr_ops);
	adf_gen4_init_pf_pfvf_ops(&hw_data->pfvf_ops);
+1 −0
Original line number Diff line number Diff line
@@ -17,6 +17,7 @@ intel_qat-objs := adf_cfg.o \
	adf_gen4_pm.o \
	adf_gen2_dc.o \
	adf_gen4_dc.o \
	adf_gen4_timer.o \
	qat_crypto.o \
	qat_compression.o \
	qat_comp_algs.o \
+3 −0
Original line number Diff line number Diff line
@@ -188,6 +188,8 @@ struct adf_hw_device_data {
	int (*init_admin_comms)(struct adf_accel_dev *accel_dev);
	void (*exit_admin_comms)(struct adf_accel_dev *accel_dev);
	int (*send_admin_init)(struct adf_accel_dev *accel_dev);
	int (*start_timer)(struct adf_accel_dev *accel_dev);
	void (*stop_timer)(struct adf_accel_dev *accel_dev);
	int (*init_arb)(struct adf_accel_dev *accel_dev);
	void (*exit_arb)(struct adf_accel_dev *accel_dev);
	const u32 *(*get_arb_mapping)(struct adf_accel_dev *accel_dev);
@@ -296,6 +298,7 @@ struct adf_accel_dev {
	struct list_head list;
	struct module *owner;
	struct adf_accel_pci accel_pci_dev;
	struct adf_timer *timer;
	union {
		struct {
			/* protects VF2PF interrupts access */
+12 −0
Original line number Diff line number Diff line
@@ -241,6 +241,18 @@ int adf_get_ae_fw_counters(struct adf_accel_dev *accel_dev, u16 ae, u64 *reqs, u
	return 0;
}

int adf_send_admin_tim_sync(struct adf_accel_dev *accel_dev, u32 cnt)
{
	u32 ae_mask = accel_dev->hw_device->ae_mask;
	struct icp_qat_fw_init_admin_req req = { };
	struct icp_qat_fw_init_admin_resp resp = { };

	req.cmd_id = ICP_QAT_FW_SYNC;
	req.int_timer_ticks = cnt;

	return adf_send_admin(accel_dev, &req, &resp, ae_mask);
}

/**
 * adf_send_admin_init() - Function sends init message to FW
 * @accel_dev: Pointer to acceleration device.
+3 −0
Original line number Diff line number Diff line
@@ -96,6 +96,7 @@ void adf_exit_admin_comms(struct adf_accel_dev *accel_dev);
int adf_send_admin_init(struct adf_accel_dev *accel_dev);
int adf_get_ae_fw_counters(struct adf_accel_dev *accel_dev, u16 ae, u64 *reqs, u64 *resps);
int adf_init_admin_pm(struct adf_accel_dev *accel_dev, u32 idle_delay);
int adf_send_admin_tim_sync(struct adf_accel_dev *accel_dev, u32 cnt);
int adf_init_arb(struct adf_accel_dev *accel_dev);
void adf_exit_arb(struct adf_accel_dev *accel_dev);
void adf_update_ring_arb(struct adf_etr_ring_data *ring);
@@ -194,6 +195,8 @@ int qat_uclo_set_cfg_ae_mask(struct icp_qat_fw_loader_handle *handle,
int adf_init_misc_wq(void);
void adf_exit_misc_wq(void);
bool adf_misc_wq_queue_work(struct work_struct *work);
bool adf_misc_wq_queue_delayed_work(struct delayed_work *work,
				    unsigned long delay);
#if defined(CONFIG_PCI_IOV)
int adf_sriov_configure(struct pci_dev *pdev, int numvfs);
void adf_disable_sriov(struct adf_accel_dev *accel_dev);
Loading