Commit 94cc1bf4 authored by Daniel Leung's avatar Daniel Leung Committed by Anas Nashif
Browse files

ipm: remove ipm_cavs_idc driver

The ipm_cavs_idc driver was used with the old intel_s1000
board which has been removed. On the audio DSP side,
the IDC under CAVS is being handled by SoC layer code.
Now the ipm_cavs_idc is not needed anymore for anything.
So remove it.

Signed-off-by: default avatarDaniel Leung <daniel.leung@intel.com>
parent f6185221
Loading
Loading
Loading
Loading
+0 −1
Changes for drivers/ipm/CMakeLists.txt: 0 added lines, 1 removed line.
Original line number Diff line number Diff line
@@ -10,7 +10,6 @@ zephyr_library_sources_ifdef(CONFIG_IPM_IMX_REV2 ipm_imx.c)
zephyr_library_sources_ifdef(CONFIG_IPM_MHU ipm_mhu.c)
zephyr_library_sources_ifdef(CONFIG_IPM_STM32_IPCC ipm_stm32_ipcc.c)
zephyr_library_sources_ifdef(CONFIG_IPM_NRFX ipm_nrfx_ipc.c)
zephyr_library_sources_ifdef(CONFIG_IPM_CAVS_IDC ipm_cavs_idc.c)
zephyr_library_sources_ifdef(CONFIG_IPM_STM32_HSEM ipm_stm32_hsem.c)
zephyr_library_sources_ifdef(CONFIG_IPM_CAVS_HOST ipm_cavs_host.c)
zephyr_library_sources_ifdef(CONFIG_IPM_SEDI ipm_sedi.c)
+0 −8
Changes for drivers/ipm/Kconfig.intel_adsp: 0 added lines, 8 removed lines.
Original line number Diff line number Diff line
# SPDX-License-Identifier: Apache-2.0
# Copyright (c) 2022, Intel Corporation

config IPM_CAVS_IDC
	bool "CAVS DSP Intra-DSP Communication (IDC) driver"
	default y if MP_NUM_CPUS > 1 && SMP
	depends on CAVS_ICTL && DT_HAS_INTEL_ADSP_IDC_ENABLED
	help
	  Driver for the Intra-DSP Communication (IDC) channel for
	  cross SoC communications.

config IPM_CALLBACK_ASYNC
	bool "Deliver callbacks asynchronously"
	default y if IPM_CAVS_HOST

drivers/ipm/ipm_cavs_idc.c

deleted100644 → 0
+0 −242
Changes for drivers/ipm/ipm_cavs_idc.c: 0 added lines, 242 removed lines.
Original line number Diff line number Diff line
/*
 * Copyright (c) 2020 Intel Corporation
 *
 * SPDX-License-Identifier: Apache-2.0
 */
#include <stdint.h>
#include <zephyr/device.h>
#include <zephyr/init.h>
#include <zephyr/drivers/ipm.h>
#include <zephyr/arch/common/sys_io.h>

#include <soc.h>
#include <zephyr/irq.h>
#include "ipm_cavs_idc.h"

#ifdef CONFIG_SCHED_IPI_SUPPORTED
extern void z_sched_ipi(void);
#endif

struct cavs_idc_data {
	ipm_callback_t	cb;
	void		*user_data;
};

static struct cavs_idc_data cavs_idc_device_data;

static void cavs_idc_isr(const struct device *dev)
{
	struct cavs_idc_data *drv_data = dev->data;

	uint32_t i, id;
	void *ext;
	uint32_t idctfc;
	uint32_t curr_cpu_id = arch_curr_cpu()->id;
#ifdef CONFIG_SCHED_IPI_SUPPORTED
	bool do_sched_ipi = false;
#endif

	unsigned int num_cpus = arch_num_cpus();

	for (i = 0; i < num_cpus; i++) {
		if (i == curr_cpu_id) {
			/* skip current core */
			continue;
		}

		idctfc = idc_read(IPC_IDCTFC(i), curr_cpu_id);

		if ((idctfc & IPC_IDCTFC_BUSY) == 0) {
			/* No message from this core */
			continue;
		}

		/* Extract the message */
		id = idctfc & IPC_IDCTFC_MSG_MASK;

		switch (id) {
#ifdef CONFIG_SCHED_IPI_SUPPORTED
		case IPM_CAVS_IDC_MSG_SCHED_IPI_ID:
			do_sched_ipi = true;
			break;
#endif
		default:
			if (drv_data->cb != NULL) {
				ext = UINT_TO_POINTER(
					idc_read(IPC_IDCTEFC(i), curr_cpu_id) &
					IPC_IDCTEFC_MSG_MASK);
				drv_data->cb(dev, drv_data->user_data, id, ext);
			}
			break;
		}

		/* Reset busy bit by writing to it */
		idctfc |= IPC_IDCTFC_BUSY;
		idc_write(IPC_IDCTFC(i), curr_cpu_id, idctfc);
	}
#ifdef CONFIG_SCHED_IPI_SUPPORTED
	if (do_sched_ipi) {
		z_sched_ipi();
	}
#endif
}

static int cavs_idc_send(const struct device *dev, int wait, uint32_t id,
			 const void *data, int size)
{
	uint32_t curr_cpu_id = arch_curr_cpu()->id;
	uint32_t ext = POINTER_TO_UINT(data);
	uint32_t reg;
	bool busy;
	int i;

	if ((wait != 0) || (size != 0)) {
		return -ENOTSUP;
	}

	/* Check if any core is still busy */
	busy = false;
	unsigned int num_cpus = arch_num_cpus();

	for (i = 0; i < num_cpus; i++) {
		if (i == curr_cpu_id) {
			/* skip current core */
			continue;
		}

		reg = idc_read(IPC_IDCITC(i), curr_cpu_id);
		if ((reg & IPC_IDCITC_BUSY) != 0) {
			busy = true;
			break;
		}
	}

	/* Can't send if busy */
	if (busy) {
		return -EBUSY;
	}

	id &= IPC_IDCITC_MSG_MASK;
	ext &= IPC_IDCIETC_MSG_MASK;
	ext |= IPC_IDCIETC_DONE; /* always clear DONE bit */

	for (i = 0; i < num_cpus; i++) {
		if (i == curr_cpu_id) {
			/* skip current core */
			continue;
		}

		idc_write(IPC_IDCIETC(i), curr_cpu_id, ext);
		idc_write(IPC_IDCITC(i), curr_cpu_id, id | IPC_IDCITC_BUSY);
	}

	return 0;
}

static int cavs_idc_max_data_size_get(const struct device *dev)
{
	ARG_UNUSED(dev);

	/* IDC can send an ID (of 31 bits, the header) and
	 * another data of 30 bits (the extension). It cannot
	 * send a whole message over. Best we can do is send
	 * a 4-byte aligned pointer.
	 *
	 * So return 0 here for max data size.
	 */

	return 0;
}

static uint32_t cavs_idc_max_id_val_get(const struct device *dev)
{
	ARG_UNUSED(dev);

	return IPM_CAVS_IDC_ID_MASK;
}

static void cavs_idc_register_callback(const struct device *dev,
				       ipm_callback_t cb,
				       void *user_data)
{
	struct cavs_idc_data *drv_data = dev->data;

	drv_data->cb = cb;
	drv_data->user_data = user_data;
}

static int cavs_idc_set_enabled(const struct device *dev, int enable)
{
	int i, j;
	uint32_t mask;

#ifdef CONFIG_SCHED_IPI_SUPPORTED
	/* With scheduler IPI, IDC must always be enabled. */
	if (enable == 0) {
		return -ENOTSUP;
	}
#endif

	unsigned int num_cpus = arch_num_cpus();

	for (i = 0; i < num_cpus; i++) {
		mask = 0;

		if (enable) {
			for (j = 0; j < num_cpus; j++) {
				if (i == j) {
					continue;
				}

				mask |= IPC_IDCCTL_IDCTBIE(j);
			}
		}

		idc_write(IPC_IDCCTL, i, mask);

		/* FIXME: when we have API to enable IRQ on specific core. */
		sys_set_bit(DT_REG_ADDR(DT_NODELABEL(cavs_intc0)) + 0x04 +
			    CAVS_ICTL_INT_CPU_OFFSET(i),
			    CAVS_IRQ_NUMBER(DT_INST_IRQN(0)));
	}

	return 0;
}

static int cavs_idc_init(const struct device *dev)
{
	IRQ_CONNECT(DT_INST_IRQN(0),
		    DT_INST_IRQ(0, priority),
		    cavs_idc_isr, DEVICE_DT_INST_GET(0), 0);

	irq_enable(DT_INST_IRQN(0));

	return 0;
}

static const struct ipm_driver_api cavs_idc_driver_api = {
	.send = cavs_idc_send,
	.register_callback = cavs_idc_register_callback,
	.max_data_size_get = cavs_idc_max_data_size_get,
	.max_id_val_get = cavs_idc_max_id_val_get,
	.set_enabled = cavs_idc_set_enabled,
};

DEVICE_DT_INST_DEFINE(0, &cavs_idc_init, NULL,
		    &cavs_idc_device_data, NULL,
		    PRE_KERNEL_2, CONFIG_KERNEL_INIT_PRIORITY_DEFAULT,
		    &cavs_idc_driver_api);

#ifdef CONFIG_SCHED_IPI_SUPPORTED
int cavs_idc_smp_init(void)
{
	/* Enable IDC for scheduler IPI */
	cavs_idc_set_enabled(dev, 1);

	return 0;
}

#ifndef CONFIG_SMP_BOOT_DELAY
SYS_INIT(cavs_idc_smp_init, SMP, 0);
#endif
#endif

drivers/ipm/ipm_cavs_idc.h

deleted100644 → 0
+0 −68
Changes for drivers/ipm/ipm_cavs_idc.h: 0 added lines, 68 removed lines.
Original line number Diff line number Diff line
/*
 * Copyright (c) 2020 Intel Corporation
 *
 * SPDX-License-Identifier: Apache-2.0
 */

#ifndef ZEPHYR_DRIVERS_IPM_IPM_CAVS_IDC_H_
#define ZEPHYR_DRIVERS_IPM_IPM_CAVS_IDC_H_

#define DT_DRV_COMPAT intel_adsp_idc
#include <intel_adsp_ipc_devtree.h>

/* Redeclaration of the earlier IDC register API for platforms being
 * held back on this driver.
 */
# ifndef IPC_DSP_BASE
# define IPC_DSP_BASE(core)    (INTEL_ADSP_IDC_REG_ADDRESS + 0x80 * (core))
# endif
#define IPC_IDCTFC(x)         (x * 0x10)
#define IPC_IDCTFC_BUSY       BIT(31)
#define IPC_IDCTFC_MSG_MASK   0x7FFFFFFF
#define IPC_IDCTEFC(x)        (0x4 + x * 0x10)
#define IPC_IDCTEFC_MSG_MASK  0x3FFFFFFF
#define IPC_IDCITC(x)         (0x8 + x * 0x10)
#define IPC_IDCITC_MSG_MASK   0x7FFFFFFF
#define IPC_IDCITC_BUSY       BIT(31)
#define IPC_IDCIETC(x)        (0xc + x * 0x10)
#define IPC_IDCIETC_MSG_MASK  0x3FFFFFFF
#define IPC_IDCIETC_DONE      BIT(30)
#define IPC_IDCCTL            0x50
#define IPC_IDCCTL_IDCTBIE(x) BIT(x)

#define IPM_CAVS_IDC_ID_MASK			\
	(CAVS_IDC_TYPE(CAVS_IDC_TYPE_MASK) |	\
	 CAVS_IDC_HEADER(CAVS_IDC_HEADER_MASK))

/* IDC message type. */
#define CAVS_IDC_TYPE_SHIFT		24U
#define CAVS_IDC_TYPE_MASK		0x7FU
#define CAVS_IDC_TYPE(x)		\
	(((x) & CAVS_IDC_TYPE_MASK) << CAVS_IDC_TYPE_SHIFT)

/* IDC message header. */
#define CAVS_IDC_HEADER_MASK		0xFFFFFFU
#define CAVS_IDC_HEADER(x)		((x) & CAVS_IDC_HEADER_MASK)

/* IDC message extension. */
#define CAVS_IDC_EXTENSION_MASK		0x3FFFFFFFU
#define CAVS_IDC_EXTENSION(x)		((x) & CAVS_IDC_EXTENSION_MASK)

/* Scheduler IPI message (type 0x7F, header 'IPI' in ascii) */
#define IPM_CAVS_IDC_MSG_SCHED_IPI_DATA		0
#define IPM_CAVS_IDC_MSG_SCHED_IPI_ID		\
	(CAVS_IDC_TYPE(0x7FU) | CAVS_IDC_HEADER(0x495049U))

static inline uint32_t idc_read(uint32_t reg, uint32_t core_id)
{
	return *((volatile uint32_t*)(IPC_DSP_BASE(core_id) + reg));
}

static inline void idc_write(uint32_t reg, uint32_t core_id, uint32_t val)
{
	*((volatile uint32_t*)(IPC_DSP_BASE(core_id) + reg)) = val;
}

int cavs_idc_smp_init(const struct device *dev);

#endif /* ZEPHYR_DRIVERS_IPM_IPM_CAVS_IDC_H_ */
+0 −1
Changes for tests/boards/intel_adsp/smoke/prj.conf: 0 added lines, 1 removed line.
Original line number Diff line number Diff line
@@ -5,4 +5,3 @@ CONFIG_SMP_BOOT_DELAY=y
CONFIG_SCHED_CPU_MASK=y
CONFIG_IPM=y
CONFIG_IPM_CAVS_HOST=y
CONFIG_IPM_CAVS_IDC=n