// SPDX-License-Identifier: BSD-3-Clause-Clear
/*
 * Copyright (c) 2019-2020 The Linux Foundation. All rights reserved.
 */

#include <linux/relay.h>
#include "core.h"
#include "debug.h"

#define ATH11K_SPECTRAL_NUM_RESP_PER_EVENT	2
#define ATH11K_SPECTRAL_EVENT_TIMEOUT_MS	1

#define ATH11K_SPECTRAL_DWORD_SIZE		4
/* HW bug, expected BIN size is 2 bytes but HW report as 4 bytes */
#define ATH11K_SPECTRAL_BIN_SIZE		4
#define ATH11K_SPECTRAL_ATH11K_MIN_BINS		64
#define ATH11K_SPECTRAL_ATH11K_MIN_IB_BINS	32
#define ATH11K_SPECTRAL_ATH11K_MAX_IB_BINS	256

#define ATH11K_SPECTRAL_SCAN_COUNT_MAX		4095

/* Max channel computed by sum of 2g and 5g band channels */
#define ATH11K_SPECTRAL_TOTAL_CHANNEL		41
#define ATH11K_SPECTRAL_SAMPLES_PER_CHANNEL	70
#define ATH11K_SPECTRAL_PER_SAMPLE_SIZE		(sizeof(struct fft_sample_ath11k) + \
						 ATH11K_SPECTRAL_ATH11K_MAX_IB_BINS)
#define ATH11K_SPECTRAL_TOTAL_SAMPLE		(ATH11K_SPECTRAL_TOTAL_CHANNEL * \
						 ATH11K_SPECTRAL_SAMPLES_PER_CHANNEL)
#define ATH11K_SPECTRAL_SUB_BUFF_SIZE		ATH11K_SPECTRAL_PER_SAMPLE_SIZE
#define ATH11K_SPECTRAL_NUM_SUB_BUF		ATH11K_SPECTRAL_TOTAL_SAMPLE

#define ATH11K_SPECTRAL_20MHZ			20
#define ATH11K_SPECTRAL_40MHZ			40
#define ATH11K_SPECTRAL_80MHZ			80

#define ATH11K_SPECTRAL_SIGNATURE		0xFA

#define ATH11K_SPECTRAL_TAG_RADAR_SUMMARY	0x0
#define ATH11K_SPECTRAL_TAG_RADAR_FFT		0x1
#define ATH11K_SPECTRAL_TAG_SCAN_SUMMARY	0x2
#define ATH11K_SPECTRAL_TAG_SCAN_SEARCH		0x3

#define SPECTRAL_TLV_HDR_LEN				GENMASK(15, 0)
#define SPECTRAL_TLV_HDR_TAG				GENMASK(23, 16)
#define SPECTRAL_TLV_HDR_SIGN				GENMASK(31, 24)

#define SPECTRAL_SUMMARY_INFO0_AGC_TOTAL_GAIN		GENMASK(7, 0)
#define SPECTRAL_SUMMARY_INFO0_OB_FLAG			BIT(8)
#define SPECTRAL_SUMMARY_INFO0_GRP_IDX			GENMASK(16, 9)
#define SPECTRAL_SUMMARY_INFO0_RECENT_RFSAT		BIT(17)
#define SPECTRAL_SUMMARY_INFO0_INBAND_PWR_DB		GENMASK(27, 18)
#define SPECTRAL_SUMMARY_INFO0_FALSE_SCAN		BIT(28)
#define SPECTRAL_SUMMARY_INFO0_DETECTOR_ID		GENMASK(30, 29)
#define SPECTRAL_SUMMARY_INFO0_PRI80			BIT(31)

#define SPECTRAL_SUMMARY_INFO2_PEAK_SIGNED_IDX		GENMASK(11, 0)
#define SPECTRAL_SUMMARY_INFO2_PEAK_MAGNITUDE		GENMASK(21, 12)
#define SPECTRAL_SUMMARY_INFO2_NARROWBAND_MASK		GENMASK(29, 22)
#define SPECTRAL_SUMMARY_INFO2_GAIN_CHANGE		BIT(30)

struct spectral_tlv {
	__le32 timestamp;
	__le32 header;
} __packed;

struct spectral_summary_fft_report {
	__le32 timestamp;
	__le32 tlv_header;
	__le32 info0;
	__le32 reserve0;
	__le32 info2;
	__le32 reserve1;
} __packed;

struct ath11k_spectral_summary_report {
	struct wmi_dma_buf_release_meta_data meta;
	u32 timestamp;
	u8 agc_total_gain;
	u8 grp_idx;
	u16 inb_pwr_db;
	s16 peak_idx;
	u16 peak_mag;
	u8 detector_id;
	bool out_of_band_flag;
	bool rf_saturation;
	bool primary80;
	bool gain_change;
	bool false_scan;
};

#define SPECTRAL_FFT_REPORT_INFO0_DETECTOR_ID		GENMASK(1, 0)
#define SPECTRAL_FFT_REPORT_INFO0_FFT_NUM		GENMASK(4, 2)
#define SPECTRAL_FFT_REPORT_INFO0_RADAR_CHECK		GENMASK(16, 5)
#define SPECTRAL_FFT_REPORT_INFO0_PEAK_SIGNED_IDX	GENMASK(27, 17)
#define SPECTRAL_FFT_REPORT_INFO0_CHAIN_IDX		GENMASK(30, 28)

#define SPECTRAL_FFT_REPORT_INFO1_BASE_PWR_DB		GENMASK(8, 0)
#define SPECTRAL_FFT_REPORT_INFO1_TOTAL_GAIN_DB		GENMASK(16, 9)

#define SPECTRAL_FFT_REPORT_INFO2_NUM_STRONG_BINS	GENMASK(7, 0)
#define SPECTRAL_FFT_REPORT_INFO2_PEAK_MAGNITUDE	GENMASK(17, 8)
#define SPECTRAL_FFT_REPORT_INFO2_AVG_PWR_DB		GENMASK(24, 18)
#define SPECTRAL_FFT_REPORT_INFO2_REL_PWR_DB		GENMASK(31, 25)

struct spectral_search_fft_report {
	__le32 timestamp;
	__le32 tlv_header;
	__le32 info0;
	__le32 info1;
	__le32 info2;
	__le32 reserve0;
	u8 bins[0];
} __packed;

struct ath11k_spectral_search_report {
	u32 timestamp;
	u8 detector_id;
	u8 fft_count;
	u16 radar_check;
	s16 peak_idx;
	u8 chain_idx;
	u16 base_pwr_db;
	u8 total_gain_db;
	u8 strong_bin_count;
	u16 peak_mag;
	u8 avg_pwr_db;
	u8 rel_pwr_db;
};

static struct dentry *create_buf_file_handler(const char *filename,
					      struct dentry *parent,
					      umode_t mode,
					      struct rchan_buf *buf,
					      int *is_global)
{
	struct dentry *buf_file;

	buf_file = debugfs_create_file(filename, mode, parent, buf,
				       &relay_file_operations);
	*is_global = 1;
	return buf_file;
}

static int remove_buf_file_handler(struct dentry *dentry)
{
	debugfs_remove(dentry);

	return 0;
}

static const struct rchan_callbacks rfs_scan_cb = {
	.create_buf_file = create_buf_file_handler,
	.remove_buf_file = remove_buf_file_handler,
};

static struct ath11k_vif *ath11k_spectral_get_vdev(struct ath11k *ar)
{
	struct ath11k_vif *arvif;

	lockdep_assert_held(&ar->conf_mutex);

	if (list_empty(&ar->arvifs))
		return NULL;

	/* if there already is a vif doing spectral, return that. */
	list_for_each_entry(arvif, &ar->arvifs, list)
		if (arvif->spectral_enabled)
			return arvif;

	/* otherwise, return the first vif. */
	return list_first_entry(&ar->arvifs, typeof(*arvif), list);
}

static int ath11k_spectral_scan_trigger(struct ath11k *ar)
{
	struct ath11k_vif *arvif;
	int ret;

	lockdep_assert_held(&ar->conf_mutex);

	arvif = ath11k_spectral_get_vdev(ar);
	if (!arvif)
		return -ENODEV;

	if (ar->spectral.mode == ATH11K_SPECTRAL_DISABLED)
		return 0;

	ret = ath11k_wmi_vdev_spectral_enable(ar, arvif->vdev_id,
					      ATH11K_WMI_SPECTRAL_TRIGGER_CMD_CLEAR,
					      ATH11K_WMI_SPECTRAL_ENABLE_CMD_ENABLE);
	if (ret)
		return ret;

	ret = ath11k_wmi_vdev_spectral_enable(ar, arvif->vdev_id,
					      ATH11K_WMI_SPECTRAL_TRIGGER_CMD_TRIGGER,
					      ATH11K_WMI_SPECTRAL_ENABLE_CMD_ENABLE);
	if (ret)
		return ret;

	return 0;
}

static int ath11k_spectral_scan_config(struct ath11k *ar,
				       enum ath11k_spectral_mode mode)
{
	struct ath11k_wmi_vdev_spectral_conf_param param = { 0 };
	struct ath11k_vif *arvif;
	int ret, count;

	lockdep_assert_held(&ar->conf_mutex);

	arvif = ath11k_spectral_get_vdev(ar);
	if (!arvif)
		return -ENODEV;

	arvif->spectral_enabled = (mode != ATH11K_SPECTRAL_DISABLED);
	ar->spectral.mode = mode;

	ret = ath11k_wmi_vdev_spectral_enable(ar, arvif->vdev_id,
					      ATH11K_WMI_SPECTRAL_TRIGGER_CMD_CLEAR,
					      ATH11K_WMI_SPECTRAL_ENABLE_CMD_DISABLE);
	if (ret) {
		ath11k_warn(ar->ab, "failed to enable spectral scan: %d\n", ret);
		return ret;
	}

	if (mode == ATH11K_SPECTRAL_DISABLED)
		return 0;

	if (mode == ATH11K_SPECTRAL_BACKGROUND)
		count = ATH11K_WMI_SPECTRAL_COUNT_DEFAULT;
	else
		count = max_t(u16, 1, ar->spectral.count);

	param.vdev_id = arvif->vdev_id;
	param.scan_count = count;
	param.scan_fft_size = ar->spectral.fft_size;
	param.scan_period = ATH11K_WMI_SPECTRAL_PERIOD_DEFAULT;
	param.scan_priority = ATH11K_WMI_SPECTRAL_PRIORITY_DEFAULT;
	param.scan_gc_ena = ATH11K_WMI_SPECTRAL_GC_ENA_DEFAULT;
	param.scan_restart_ena = ATH11K_WMI_SPECTRAL_RESTART_ENA_DEFAULT;
	param.scan_noise_floor_ref = ATH11K_WMI_SPECTRAL_NOISE_FLOOR_REF_DEFAULT;
	param.scan_init_delay = ATH11K_WMI_SPECTRAL_INIT_DELAY_DEFAULT;
	param.scan_nb_tone_thr = ATH11K_WMI_SPECTRAL_NB_TONE_THR_DEFAULT;
	param.scan_str_bin_thr = ATH11K_WMI_SPECTRAL_STR_BIN_THR_DEFAULT;
	param.scan_wb_rpt_mode = ATH11K_WMI_SPECTRAL_WB_RPT_MODE_DEFAULT;
	param.scan_rssi_rpt_mode = ATH11K_WMI_SPECTRAL_RSSI_RPT_MODE_DEFAULT;
	param.scan_rssi_thr = ATH11K_WMI_SPECTRAL_RSSI_THR_DEFAULT;
	param.scan_pwr_format = ATH11K_WMI_SPECTRAL_PWR_FORMAT_DEFAULT;
	param.scan_rpt_mode = ATH11K_WMI_SPECTRAL_RPT_MODE_DEFAULT;
	param.scan_bin_scale = ATH11K_WMI_SPECTRAL_BIN_SCALE_DEFAULT;
	param.scan_dbm_adj = ATH11K_WMI_SPECTRAL_DBM_ADJ_DEFAULT;
	param.scan_chn_mask = ATH11K_WMI_SPECTRAL_CHN_MASK_DEFAULT;

	ret = ath11k_wmi_vdev_spectral_conf(ar, &param);
	if (ret) {
		ath11k_warn(ar->ab, "failed to configure spectral scan: %d\n", ret);
		return ret;
	}

	return 0;
}

static ssize_t ath11k_read_file_spec_scan_ctl(struct file *file,
					      char __user *user_buf,
					      size_t count, loff_t *ppos)
{
	struct ath11k *ar = file->private_data;
	char *mode = "";
	size_t len;
	enum ath11k_spectral_mode spectral_mode;

	mutex_lock(&ar->conf_mutex);
	spectral_mode = ar->spectral.mode;
	mutex_unlock(&ar->conf_mutex);

	switch (spectral_mode) {
	case ATH11K_SPECTRAL_DISABLED:
		mode = "disable";
		break;
	case ATH11K_SPECTRAL_BACKGROUND:
		mode = "background";
		break;
	case ATH11K_SPECTRAL_MANUAL:
		mode = "manual";
		break;
	}

	len = strlen(mode);
	return simple_read_from_buffer(user_buf, count, ppos, mode, len);
}

static ssize_t ath11k_write_file_spec_scan_ctl(struct file *file,
					       const char __user *user_buf,
					       size_t count, loff_t *ppos)
{
	struct ath11k *ar = file->private_data;
	char buf[32];
	ssize_t len;
	int ret;

	len = min(count, sizeof(buf) - 1);
	if (copy_from_user(buf, user_buf, len))
		return -EFAULT;

	buf[len] = '\0';

	mutex_lock(&ar->conf_mutex);

	if (strncmp("trigger", buf, 7) == 0) {
		if (ar->spectral.mode == ATH11K_SPECTRAL_MANUAL ||
		    ar->spectral.mode == ATH11K_SPECTRAL_BACKGROUND) {
			/* reset the configuration to adopt possibly changed
			 * debugfs parameters
			 */
			ret = ath11k_spectral_scan_config(ar, ar->spectral.mode);
			if (ret) {
				ath11k_warn(ar->ab, "failed to reconfigure spectral scan: %d\n",
					    ret);
				goto unlock;
			}

			ret = ath11k_spectral_scan_trigger(ar);
			if (ret) {
				ath11k_warn(ar->ab, "failed to trigger spectral scan: %d\n",
					    ret);
			}
		} else {
			ret = -EINVAL;
		}
	} else if (strncmp("background", buf, 10) == 0) {
		ret = ath11k_spectral_scan_config(ar, ATH11K_SPECTRAL_BACKGROUND);
	} else if (strncmp("manual", buf, 6) == 0) {
		ret = ath11k_spectral_scan_config(ar, ATH11K_SPECTRAL_MANUAL);
	} else if (strncmp("disable", buf, 7) == 0) {
		ret = ath11k_spectral_scan_config(ar, ATH11K_SPECTRAL_DISABLED);
	} else {
		ret = -EINVAL;
	}

unlock:
	mutex_unlock(&ar->conf_mutex);

	if (ret)
		return ret;

	return count;
}

static const struct file_operations fops_scan_ctl = {
	.read = ath11k_read_file_spec_scan_ctl,
	.write = ath11k_write_file_spec_scan_ctl,
	.open = simple_open,
	.owner = THIS_MODULE,
	.llseek = default_llseek,
};

static ssize_t ath11k_read_file_spectral_count(struct file *file,
					       char __user *user_buf,
					       size_t count, loff_t *ppos)
{
	struct ath11k *ar = file->private_data;
	char buf[32];
	size_t len;
	u16 spectral_count;

	mutex_lock(&ar->conf_mutex);
	spectral_count = ar->spectral.count;
	mutex_unlock(&ar->conf_mutex);

	len = sprintf(buf, "%d\n", spectral_count);
	return simple_read_from_buffer(user_buf, count, ppos, buf, len);
}

static ssize_t ath11k_write_file_spectral_count(struct file *file,
						const char __user *user_buf,
						size_t count, loff_t *ppos)
{
	struct ath11k *ar = file->private_data;
	unsigned long val;
	char buf[32];
	ssize_t len;

	len = min(count, sizeof(buf) - 1);
	if (copy_from_user(buf, user_buf, len))
		return -EFAULT;

	buf[len] = '\0';
	if (kstrtoul(buf, 0, &val))
		return -EINVAL;

	if (val > ATH11K_SPECTRAL_SCAN_COUNT_MAX)
		return -EINVAL;

	mutex_lock(&ar->conf_mutex);
	ar->spectral.count = val;
	mutex_unlock(&ar->conf_mutex);

	return count;
}

static const struct file_operations fops_scan_count = {
	.read = ath11k_read_file_spectral_count,
	.write = ath11k_write_file_spectral_count,
	.open = simple_open,
	.owner = THIS_MODULE,
	.llseek = default_llseek,
};

static ssize_t ath11k_read_file_spectral_bins(struct file *file,
					      char __user *user_buf,
					      size_t count, loff_t *ppos)
{
	struct ath11k *ar = file->private_data;
	char buf[32];
	unsigned int bins, fft_size;
	size_t len;

	mutex_lock(&ar->conf_mutex);

	fft_size = ar->spectral.fft_size;
	bins = 1 << fft_size;

	mutex_unlock(&ar->conf_mutex);

	len = sprintf(buf, "%d\n", bins);
	return simple_read_from_buffer(user_buf, count, ppos, buf, len);
}

static ssize_t ath11k_write_file_spectral_bins(struct file *file,
					       const char __user *user_buf,
					       size_t count, loff_t *ppos)
{
	struct ath11k *ar = file->private_data;
	unsigned long val;
	char buf[32];
	ssize_t len;

	len = min(count, sizeof(buf) - 1);
	if (copy_from_user(buf, user_buf, len))
		return -EFAULT;

	buf[len] = '\0';
	if (kstrtoul(buf, 0, &val))
		return -EINVAL;

	if (val < ATH11K_SPECTRAL_ATH11K_MIN_BINS ||
	    val > SPECTRAL_ATH11K_MAX_NUM_BINS)
		return -EINVAL;

	if (!is_power_of_2(val))
		return -EINVAL;

	mutex_lock(&ar->conf_mutex);
	ar->spectral.fft_size = ilog2(val);
	mutex_unlock(&ar->conf_mutex);

	return count;
}

static const struct file_operations fops_scan_bins = {
	.read = ath11k_read_file_spectral_bins,
	.write = ath11k_write_file_spectral_bins,
	.open = simple_open,
	.owner = THIS_MODULE,
	.llseek = default_llseek,
};

static int ath11k_spectral_pull_summary(struct ath11k *ar,
					struct wmi_dma_buf_release_meta_data *meta,
					struct spectral_summary_fft_report *summary,
					struct ath11k_spectral_summary_report *report)
{
	report->timestamp = __le32_to_cpu(summary->timestamp);
	report->agc_total_gain = FIELD_GET(SPECTRAL_SUMMARY_INFO0_AGC_TOTAL_GAIN,
					   __le32_to_cpu(summary->info0));
	report->out_of_band_flag = FIELD_GET(SPECTRAL_SUMMARY_INFO0_OB_FLAG,
					     __le32_to_cpu(summary->info0));
	report->grp_idx = FIELD_GET(SPECTRAL_SUMMARY_INFO0_GRP_IDX,
				    __le32_to_cpu(summary->info0));
	report->rf_saturation = FIELD_GET(SPECTRAL_SUMMARY_INFO0_RECENT_RFSAT,
					  __le32_to_cpu(summary->info0));
	report->inb_pwr_db = FIELD_GET(SPECTRAL_SUMMARY_INFO0_INBAND_PWR_DB,
				       __le32_to_cpu(summary->info0));
	report->false_scan = FIELD_GET(SPECTRAL_SUMMARY_INFO0_FALSE_SCAN,
				       __le32_to_cpu(summary->info0));
	report->detector_id = FIELD_GET(SPECTRAL_SUMMARY_INFO0_DETECTOR_ID,
					__le32_to_cpu(summary->info0));
	report->primary80 = FIELD_GET(SPECTRAL_SUMMARY_INFO0_PRI80,
				      __le32_to_cpu(summary->info0));
	report->peak_idx = FIELD_GET(SPECTRAL_SUMMARY_INFO2_PEAK_SIGNED_IDX,
				     __le32_to_cpu(summary->info2));
	report->peak_mag = FIELD_GET(SPECTRAL_SUMMARY_INFO2_PEAK_MAGNITUDE,
				     __le32_to_cpu(summary->info2));
	report->gain_change = FIELD_GET(SPECTRAL_SUMMARY_INFO2_GAIN_CHANGE,
					__le32_to_cpu(summary->info2));

	memcpy(&report->meta, meta, sizeof(*meta));

	return 0;
}

static int ath11k_spectral_pull_search(struct ath11k *ar,
				       struct spectral_search_fft_report *search,
				       struct ath11k_spectral_search_report *report)
{
	report->timestamp = __le32_to_cpu(search->timestamp);
	report->detector_id = FIELD_GET(SPECTRAL_FFT_REPORT_INFO0_DETECTOR_ID,
					__le32_to_cpu(search->info0));
	report->fft_count = FIELD_GET(SPECTRAL_FFT_REPORT_INFO0_FFT_NUM,
				      __le32_to_cpu(search->info0));
	report->radar_check = FIELD_GET(SPECTRAL_FFT_REPORT_INFO0_RADAR_CHECK,
					__le32_to_cpu(search->info0));
	report->peak_idx = FIELD_GET(SPECTRAL_FFT_REPORT_INFO0_PEAK_SIGNED_IDX,
				     __le32_to_cpu(search->info0));
	report->chain_idx = FIELD_GET(SPECTRAL_FFT_REPORT_INFO0_CHAIN_IDX,
				      __le32_to_cpu(search->info0));
	report->base_pwr_db = FIELD_GET(SPECTRAL_FFT_REPORT_INFO1_BASE_PWR_DB,
					__le32_to_cpu(search->info1));
	report->total_gain_db = FIELD_GET(SPECTRAL_FFT_REPORT_INFO1_TOTAL_GAIN_DB,
					  __le32_to_cpu(search->info1));
	report->strong_bin_count = FIELD_GET(SPECTRAL_FFT_REPORT_INFO2_NUM_STRONG_BINS,
					     __le32_to_cpu(search->info2));
	report->peak_mag = FIELD_GET(SPECTRAL_FFT_REPORT_INFO2_PEAK_MAGNITUDE,
				     __le32_to_cpu(search->info2));
	report->avg_pwr_db = FIELD_GET(SPECTRAL_FFT_REPORT_INFO2_AVG_PWR_DB,
				       __le32_to_cpu(search->info2));
	report->rel_pwr_db = FIELD_GET(SPECTRAL_FFT_REPORT_INFO2_REL_PWR_DB,
				       __le32_to_cpu(search->info2));

	return 0;
}

static u8 ath11k_spectral_get_max_exp(s8 max_index, u8 max_magnitude,
				      int bin_len, u8 *bins)
{
	int dc_pos;
	u8 max_exp;

	dc_pos = bin_len / 2;

	/* peak index outside of bins */
	if (dc_pos <= max_index || -dc_pos >= max_index)
		return 0;

	for (max_exp = 0; max_exp < 8; max_exp++) {
		if (bins[dc_pos + max_index] == (max_magnitude >> max_exp))
			break;
	}

	/* max_exp not found */
	if (bins[dc_pos + max_index] != (max_magnitude >> max_exp))
		return 0;

	return max_exp;
}

static void ath11k_spectral_parse_fft(u8 *outbins, u8 *inbins, int num_bins, u8 fft_sz)
{
	int i, j;

	i = 0;
	j = 0;
	while (i < num_bins) {
		outbins[i] = inbins[j];
		i++;
		j += fft_sz;
	}
}

static
int ath11k_spectral_process_fft(struct ath11k *ar,
				struct ath11k_spectral_summary_report *summary,
				void *data,
				struct fft_sample_ath11k *fft_sample,
				u32 data_len)
{
	struct ath11k_base *ab = ar->ab;
	struct spectral_search_fft_report *fft_report = data;
	struct ath11k_spectral_search_report search;
	struct spectral_tlv *tlv;
	int tlv_len, bin_len, num_bins;
	u16 length, freq;
	u8 chan_width_mhz;
	int ret;

	lockdep_assert_held(&ar->spectral.lock);

	if (!ab->hw_params.spectral_fft_sz) {
		ath11k_warn(ab, "invalid bin size type for hw rev %d\n",
			    ab->hw_rev);
		return -EINVAL;
	}

	tlv = (struct spectral_tlv *)data;
	tlv_len = FIELD_GET(SPECTRAL_TLV_HDR_LEN, __le32_to_cpu(tlv->header));
	/* convert Dword into bytes */
	tlv_len *= ATH11K_SPECTRAL_DWORD_SIZE;
	bin_len = tlv_len - (sizeof(*fft_report) - sizeof(*tlv));

	if (data_len < (bin_len + sizeof(*fft_report))) {
		ath11k_warn(ab, "mismatch in expected bin len %d and data len %d\n",
			    bin_len, data_len);
		return -EINVAL;
	}

	num_bins = bin_len / ATH11K_SPECTRAL_BIN_SIZE;
	/* Only In-band bins are useful to user for visualize */
	num_bins >>= 1;

	if (num_bins < ATH11K_SPECTRAL_ATH11K_MIN_IB_BINS ||
	    num_bins > ATH11K_SPECTRAL_ATH11K_MAX_IB_BINS ||
	    !is_power_of_2(num_bins)) {
		ath11k_warn(ab, "Invalid num of bins %d\n", num_bins);
		return -EINVAL;
	}

	ret = ath11k_spectral_pull_search(ar, data, &search);
	if (ret) {
		ath11k_warn(ab, "failed to pull search report %d\n", ret);
		return ret;
	}

	chan_width_mhz = summary->meta.ch_width;

	switch (chan_width_mhz) {
	case ATH11K_SPECTRAL_20MHZ:
	case ATH11K_SPECTRAL_40MHZ:
	case ATH11K_SPECTRAL_80MHZ:
		fft_sample->chan_width_mhz = chan_width_mhz;
		break;
	default:
		ath11k_warn(ab, "invalid channel width %d\n", chan_width_mhz);
		return -EINVAL;
	}

	length = sizeof(*fft_sample) - sizeof(struct fft_sample_tlv) + num_bins;
	fft_sample->tlv.type = ATH_FFT_SAMPLE_ATH11K;
	fft_sample->tlv.length = __cpu_to_be16(length);

	fft_sample->tsf = __cpu_to_be32(search.timestamp);
	fft_sample->max_magnitude = __cpu_to_be16(search.peak_mag);
	fft_sample->max_index = FIELD_GET(SPECTRAL_FFT_REPORT_INFO0_PEAK_SIGNED_IDX,
					  __le32_to_cpu(fft_report->info0));

	summary->inb_pwr_db >>= 1;
	fft_sample->rssi = __cpu_to_be16(summary->inb_pwr_db);
	fft_sample->noise = __cpu_to_be32(summary->meta.noise_floor[search.chain_idx]);

	freq = summary->meta.freq1;
	fft_sample->freq1 = __cpu_to_be16(freq);

	freq = summary->meta.freq2;
	fft_sample->freq2 = __cpu_to_be16(freq);

	ath11k_spectral_parse_fft(fft_sample->data, fft_report->bins, num_bins,
				  ab->hw_params.spectral_fft_sz);

	fft_sample->max_exp = ath11k_spectral_get_max_exp(fft_sample->max_index,
							  search.peak_mag,
							  num_bins,
							  fft_sample->data);

	if (ar->spectral.rfs_scan)
		relay_write(ar->spectral.rfs_scan, fft_sample,
			    length + sizeof(struct fft_sample_tlv));

	return 0;
}

static int ath11k_spectral_process_data(struct ath11k *ar,
					struct ath11k_dbring_data *param)
{
	struct ath11k_base *ab = ar->ab;
	struct spectral_tlv *tlv;
	struct spectral_summary_fft_report *summary = NULL;
	struct ath11k_spectral_summary_report summ_rpt;
	struct fft_sample_ath11k *fft_sample = NULL;
	u8 *data;
	u32 data_len, i;
	u8 sign, tag;
	int tlv_len, sample_sz;
	int ret;
	bool quit = false;

	spin_lock_bh(&ar->spectral.lock);

	if (!ar->spectral.enabled) {
		ret = -EINVAL;
		goto unlock;
	}

	sample_sz = sizeof(*fft_sample) + ATH11K_SPECTRAL_ATH11K_MAX_IB_BINS;
	fft_sample = kmalloc(sample_sz, GFP_ATOMIC);
	if (!fft_sample) {
		ret = -ENOBUFS;
		goto unlock;
	}

	data = param->data;
	data_len = param->data_sz;
	i = 0;
	while (!quit && (i < data_len)) {
		if ((i + sizeof(*tlv)) > data_len) {
			ath11k_warn(ab, "failed to parse spectral tlv hdr at bytes %d\n",
				    i);
			ret = -EINVAL;
			goto err;
		}

		tlv = (struct spectral_tlv *)&data[i];
		sign = FIELD_GET(SPECTRAL_TLV_HDR_SIGN,
				 __le32_to_cpu(tlv->header));
		if (sign != ATH11K_SPECTRAL_SIGNATURE) {
			ath11k_warn(ab, "Invalid sign 0x%x at bytes %d\n",
				    sign, i);
			ret = -EINVAL;
			goto err;
		}

		tlv_len = FIELD_GET(SPECTRAL_TLV_HDR_LEN,
				    __le32_to_cpu(tlv->header));
		/* convert Dword into bytes */
		tlv_len *= ATH11K_SPECTRAL_DWORD_SIZE;
		if ((i + sizeof(*tlv) + tlv_len) > data_len) {
			ath11k_warn(ab, "failed to parse spectral tlv payload at bytes %d tlv_len:%d data_len:%d\n",
				    i, tlv_len, data_len);
			ret = -EINVAL;
			goto err;
		}

		tag = FIELD_GET(SPECTRAL_TLV_HDR_TAG,
				__le32_to_cpu(tlv->header));
		switch (tag) {
		case ATH11K_SPECTRAL_TAG_SCAN_SUMMARY:
			/* HW bug in tlv length of summary report,
			 * HW report 3 DWORD size but the data payload
			 * is 4 DWORD size (16 bytes).
			 * Need to remove this workaround once HW bug fixed
			 */
			tlv_len = sizeof(*summary) - sizeof(*tlv);

			if (tlv_len < (sizeof(*summary) - sizeof(*tlv))) {
				ath11k_warn(ab, "failed to parse spectral summary at bytes %d tlv_len:%d\n",
					    i, tlv_len);
				ret = -EINVAL;
				goto err;
			}

			summary = (struct spectral_summary_fft_report *)tlv;
			ath11k_spectral_pull_summary(ar, &param->meta,
						     summary, &summ_rpt);
			break;
		case ATH11K_SPECTRAL_TAG_SCAN_SEARCH:
			if (tlv_len < (sizeof(struct spectral_search_fft_report) -
				       sizeof(*tlv))) {
				ath11k_warn(ab, "failed to parse spectral search fft at bytes %d\n",
					    i);
				ret = -EINVAL;
				goto err;
			}

			memset(fft_sample, 0, sample_sz);
			ret = ath11k_spectral_process_fft(ar, &summ_rpt, tlv,
							  fft_sample,
							  data_len - i);
			if (ret) {
				ath11k_warn(ab, "failed to process spectral fft at bytes %d\n",
					    i);
				goto err;
			}
			quit = true;
			break;
		}

		i += sizeof(*tlv) + tlv_len;
	}

	ret = 0;

err:
	kfree(fft_sample);
unlock:
	spin_unlock_bh(&ar->spectral.lock);
	return ret;
}

static int ath11k_spectral_ring_alloc(struct ath11k *ar,
				      struct ath11k_dbring_cap *db_cap)
{
	struct ath11k_spectral *sp = &ar->spectral;
	int ret;

	ret = ath11k_dbring_srng_setup(ar, &sp->rx_ring,
				       0, db_cap->min_elem);
	if (ret) {
		ath11k_warn(ar->ab, "failed to setup db ring\n");
		return ret;
	}

	ath11k_dbring_set_cfg(ar, &sp->rx_ring,
			      ATH11K_SPECTRAL_NUM_RESP_PER_EVENT,
			      ATH11K_SPECTRAL_EVENT_TIMEOUT_MS,
			      ath11k_spectral_process_data);

	ret = ath11k_dbring_buf_setup(ar, &sp->rx_ring, db_cap);
	if (ret) {
		ath11k_warn(ar->ab, "failed to setup db ring buffer\n");
		goto srng_cleanup;
	}

	ret = ath11k_dbring_wmi_cfg_setup(ar, &sp->rx_ring,
					  WMI_DIRECT_BUF_SPECTRAL);
	if (ret) {
		ath11k_warn(ar->ab, "failed to setup db ring cfg\n");
		goto buffer_cleanup;
	}

	return 0;

buffer_cleanup:
	ath11k_dbring_buf_cleanup(ar, &sp->rx_ring);
srng_cleanup:
	ath11k_dbring_srng_cleanup(ar, &sp->rx_ring);
	return ret;
}

static inline void ath11k_spectral_ring_free(struct ath11k *ar)
{
	struct ath11k_spectral *sp = &ar->spectral;

	if (!sp->enabled)
		return;

	ath11k_dbring_srng_cleanup(ar, &sp->rx_ring);
	ath11k_dbring_buf_cleanup(ar, &sp->rx_ring);
}

static inline void ath11k_spectral_debug_unregister(struct ath11k *ar)
{
	debugfs_remove(ar->spectral.scan_bins);
	ar->spectral.scan_bins = NULL;

	debugfs_remove(ar->spectral.scan_count);
	ar->spectral.scan_count = NULL;

	debugfs_remove(ar->spectral.scan_ctl);
	ar->spectral.scan_ctl = NULL;

	if (ar->spectral.rfs_scan) {
		relay_close(ar->spectral.rfs_scan);
		ar->spectral.rfs_scan = NULL;
	}
}

int ath11k_spectral_vif_stop(struct ath11k_vif *arvif)
{
	if (!arvif->spectral_enabled)
		return 0;

	return ath11k_spectral_scan_config(arvif->ar, ATH11K_SPECTRAL_DISABLED);
}

void ath11k_spectral_reset_buffer(struct ath11k *ar)
{
	if (!ar->spectral.enabled)
		return;

	if (ar->spectral.rfs_scan)
		relay_reset(ar->spectral.rfs_scan);
}

void ath11k_spectral_deinit(struct ath11k_base *ab)
{
	struct ath11k *ar;
	struct ath11k_spectral *sp;
	int i;

	for (i = 0; i <  ab->num_radios; i++) {
		ar = ab->pdevs[i].ar;
		sp = &ar->spectral;

		if (!sp->enabled)
			continue;

		ath11k_spectral_debug_unregister(ar);
		ath11k_spectral_ring_free(ar);

		spin_lock_bh(&sp->lock);

		sp->mode = ATH11K_SPECTRAL_DISABLED;
		sp->enabled = false;

		spin_unlock_bh(&sp->lock);
	}
}

static inline int ath11k_spectral_debug_register(struct ath11k *ar)
{
	int ret;

	ar->spectral.rfs_scan = relay_open("spectral_scan",
					   ar->debug.debugfs_pdev,
					   ATH11K_SPECTRAL_SUB_BUFF_SIZE,
					   ATH11K_SPECTRAL_NUM_SUB_BUF,
					   &rfs_scan_cb, NULL);
	if (!ar->spectral.rfs_scan) {
		ath11k_warn(ar->ab, "failed to open relay in pdev %d\n",
			    ar->pdev_idx);
		return -EINVAL;
	}

	ar->spectral.scan_ctl = debugfs_create_file("spectral_scan_ctl",
						    0600,
						    ar->debug.debugfs_pdev, ar,
						    &fops_scan_ctl);
	if (!ar->spectral.scan_ctl) {
		ath11k_warn(ar->ab, "failed to open debugfs in pdev %d\n",
			    ar->pdev_idx);
		ret = -EINVAL;
		goto debug_unregister;
	}

	ar->spectral.scan_count = debugfs_create_file("spectral_count",
						      0600,
						      ar->debug.debugfs_pdev, ar,
						      &fops_scan_count);
	if (!ar->spectral.scan_count) {
		ath11k_warn(ar->ab, "failed to open debugfs in pdev %d\n",
			    ar->pdev_idx);
		ret = -EINVAL;
		goto debug_unregister;
	}

	ar->spectral.scan_bins = debugfs_create_file("spectral_bins",
						     0600,
						     ar->debug.debugfs_pdev, ar,
						     &fops_scan_bins);
	if (!ar->spectral.scan_bins) {
		ath11k_warn(ar->ab, "failed to open debugfs in pdev %d\n",
			    ar->pdev_idx);
		ret = -EINVAL;
		goto debug_unregister;
	}

	return 0;

debug_unregister:
	ath11k_spectral_debug_unregister(ar);
	return ret;
}

int ath11k_spectral_init(struct ath11k_base *ab)
{
	struct ath11k *ar;
	struct ath11k_spectral *sp;
	struct ath11k_dbring_cap db_cap;
	int ret;
	int i;

	if (!test_bit(WMI_TLV_SERVICE_FREQINFO_IN_METADATA,
		      ab->wmi_ab.svc_map))
		return 0;

	if (!ab->hw_params.spectral_fft_sz)
		return 0;

	for (i = 0; i < ab->num_radios; i++) {
		ar = ab->pdevs[i].ar;
		sp = &ar->spectral;

		ret = ath11k_dbring_get_cap(ar->ab, ar->pdev_idx,
					    WMI_DIRECT_BUF_SPECTRAL,
					    &db_cap);
		if (ret)
			continue;

		idr_init(&sp->rx_ring.bufs_idr);
		spin_lock_init(&sp->rx_ring.idr_lock);
		spin_lock_init(&sp->lock);

		ret = ath11k_spectral_ring_alloc(ar, &db_cap);
		if (ret) {
			ath11k_warn(ab, "failed to init spectral ring for pdev %d\n",
				    i);
			goto deinit;
		}

		spin_lock_bh(&sp->lock);

		sp->mode = ATH11K_SPECTRAL_DISABLED;
		sp->count = ATH11K_WMI_SPECTRAL_COUNT_DEFAULT;
		sp->fft_size = ATH11K_WMI_SPECTRAL_FFT_SIZE_DEFAULT;
		sp->enabled = true;

		spin_unlock_bh(&sp->lock);

		ret = ath11k_spectral_debug_register(ar);
		if (ret) {
			ath11k_warn(ab, "failed to register spectral for pdev %d\n",
				    i);
			goto deinit;
		}
	}

	return 0;

deinit:
	ath11k_spectral_deinit(ab);
	return ret;
}

enum ath11k_spectral_mode ath11k_spectral_get_mode(struct ath11k *ar)
{
	if (ar->spectral.enabled)
		return ar->spectral.mode;
	else
		return ATH11K_SPECTRAL_DISABLED;
}

struct ath11k_dbring *ath11k_spectral_get_dbring(struct ath11k *ar)
{
	if (ar->spectral.enabled)
		return &ar->spectral.rx_ring;
	else
		return NULL;
}
