zdsp: add ARC DSPLIB backend for zdsp

Introduce ARC DSPLIB backend zdsp library for ARC target.
Add agu and restrict attributes to map with ARC DSPLIB

Signed-off-by: Siyuan Cheng <siyuanc@synopsys.com>
This commit is contained in:
Siyuan Cheng 2023-01-16 15:51:45 +08:00 committed by Carles Cufí
parent a0db069978
commit b475e1fcbf
10 changed files with 354 additions and 3 deletions

View file

@ -14,7 +14,7 @@ optimized. The status of the various architectures can be found below:
============ ============= ============ =============
Architecture Status Architecture Status
============ ============= ============ =============
ARC Unoptimized ARC Optimized
ARM Optimized ARM Optimized
ARM64 Optimized ARM64 Optimized
MIPS Unoptimized MIPS Unoptimized
@ -46,11 +46,13 @@ Optimizing for your architecture
If your architecture is showing as ``Unoptimized``, it's possible to add a new If your architecture is showing as ``Unoptimized``, it's possible to add a new
zDSP backend to better support it. To do that, a new Kconfig option should be zDSP backend to better support it. To do that, a new Kconfig option should be
added to `subsys/dsp/Kconfig`_ along with the required dependencies and the added to :file:`subsys/dsp/Kconfig` along with the required dependencies and the
``default`` set for ``DSP_BACKEND`` Kconfig choice. ``default`` set for ``DSP_BACKEND`` Kconfig choice.
Next, the implementation should be added at ``subsys/dsp/<backend>/`` and Next, the implementation should be added at ``subsys/dsp/<backend>/`` and
linked in at `subsys/dsp/CMakeLists.txt`_. linked in at :file:`subsys/dsp/CMakeLists.txt`. To add architecture-specific attributes,
its corresponding Kconfig option should be added to :file:`subsys/dsp/Kconfig` and use
them to update ``DSP_DATA`` and ``DSP_STATIC_DATA`` in :file:`include/zephyr/dsp/dsp.h`.
API Reference API Reference
************* *************
@ -59,3 +61,4 @@ API Reference
.. _subsys/dsp/Kconfig: https://github.com/zephyrproject-rtos/zephyr/blob/main/subsys/dsp/Kconfig .. _subsys/dsp/Kconfig: https://github.com/zephyrproject-rtos/zephyr/blob/main/subsys/dsp/Kconfig
.. _subsys/dsp/CMakeLists.txt: https://github.com/zephyrproject-rtos/zephyr/blob/main/subsys/dsp/CMakeLists.txt .. _subsys/dsp/CMakeLists.txt: https://github.com/zephyrproject-rtos/zephyr/blob/main/subsys/dsp/CMakeLists.txt
.. _include/zephyr/dsp/dsp.h: https://github.com/zephyrproject-rtos/zephyr/blob/main/include/zephyr/dsp/dsp.h

View file

@ -17,9 +17,17 @@
#define DSP_FUNC_SCOPE #define DSP_FUNC_SCOPE
#endif #endif
#ifdef CONFIG_DSP_BACKEND_HAS_AGU
#define DSP_DATA __agu
#else
#define DSP_DATA #define DSP_DATA
#endif
#ifdef CONFIG_DSP_BACKEND_HAS_XDATA_SECTION
#define DSP_STATIC_DATA DSP_DATA __attribute__((section(".Xdata")))
#else
#define DSP_STATIC_DATA DSP_DATA #define DSP_STATIC_DATA DSP_DATA
#endif
/** /**
* @brief DSP Interface * @brief DSP Interface

View file

@ -28,6 +28,8 @@ else()
-Xshift_assist -Xfpus_div -Xfpu_mac -Xfpuda -Xfpus_mpy_slow -Xshift_assist -Xfpus_div -Xfpu_mac -Xfpuda -Xfpus_mpy_slow
-Xfpus_div_slow -Xbitstream -Xtimer0 -Xtimer1) -Xfpus_div_slow -Xbitstream -Xtimer0 -Xtimer1)
zephyr_ld_option_ifdef(CONFIG_SOC_NSIM_EM11D -Hlib=em9d_nrg_fpusp -Hdsplib)
if(CONFIG_SOC_NSIM_EM11D) if(CONFIG_SOC_NSIM_EM11D)
set_property(GLOBAL PROPERTY z_arc_dsp_options -Xxy -Xagu_large -Hfxapi -Xdsp2 set_property(GLOBAL PROPERTY z_arc_dsp_options -Xxy -Xagu_large -Hfxapi -Xdsp2
-Xdsp_accshift=full -Xdsp_divsqrt=radix2 -Xdsp_complex -Xdsp_itu -Xdsp_accshift=full -Xdsp_divsqrt=radix2 -Xdsp_complex -Xdsp_itu

View file

@ -2,3 +2,4 @@
# SPDX-License-Identifier: Apache-2.0 # SPDX-License-Identifier: Apache-2.0
add_subdirectory_ifdef(CONFIG_DSP_BACKEND_CMSIS cmsis) add_subdirectory_ifdef(CONFIG_DSP_BACKEND_CMSIS cmsis)
add_subdirectory_ifdef(CONFIG_DSP_BACKEND_ARCMWDT arcmwdt)

View file

@ -13,9 +13,16 @@ if DSP
config DSP_BACKEND_HAS_STATIC config DSP_BACKEND_HAS_STATIC
bool bool
config DSP_BACKEND_HAS_AGU
bool
config DSP_BACKEND_HAS_XDATA_SECTION
bool
choice DSP_BACKEND choice DSP_BACKEND
prompt "DSP library backend selection" prompt "DSP library backend selection"
default DSP_BACKEND_CMSIS if CMSIS_DSP default DSP_BACKEND_CMSIS if CMSIS_DSP
default DSP_BACKEND_ARCMWDT if ARC && "$(ZEPHYR_TOOLCHAIN_VARIANT)" = "arcmwdt"
default DSP_BACKEND_CUSTOM default DSP_BACKEND_CUSTOM
config DSP_BACKEND_CMSIS config DSP_BACKEND_CMSIS
@ -32,6 +39,17 @@ config DSP_BACKEND_CUSTOM
Rely on the application to provide a custom DSP backend. The implementation should be Rely on the application to provide a custom DSP backend. The implementation should be
added to the 'zdsp' build target by the application or one of its modules. added to the 'zdsp' build target by the application or one of its modules.
config DSP_BACKEND_ARCMWDT
bool "Use the mwdt library as the math backend"
depends on ARCMWDT_LIBC
depends on CMSIS_DSP
select DSP_BACKEND_HAS_STATIC
select DSP_BACKEND_HAS_AGU
select DSP_BACKEND_HAS_XDATA_SECTION
help
Implement the various zephyr DSP functions using the MWDT-DSP library. This feature
requires the MetaWare toolchain and CMSIS module to be selected.
endchoice endchoice
endif # DSP endif # DSP

View file

@ -0,0 +1,8 @@
# Copyright (c) 2022 Synopsys
# SPDX-License-Identifier: Apache-2.0
zephyr_include_directories(public)
zephyr_include_directories_ifdef(CONFIG_DSP_BACKEND_ARCMWDT
${ARCMWDT_TOOLCHAIN_PATH}/MetaWare/arc/lib/src/dsp/include/
)

View file

@ -0,0 +1,293 @@
/*
* Copyright (c) 2022 Synopsys
*
* SPDX-License-Identifier: Apache-2.0
*/
#ifndef SUBSYS_MATH_ARC_BACKEND_PUBLIC_ZDSP_BACKEND_DSP_H_
#define SUBSYS_MATH_ARC_BACKEND_PUBLIC_ZDSP_BACKEND_DSP_H_
#ifdef __cplusplus
extern "C" {
#endif
/* This include MUST be done before arm_math.h so we can let the arch specific
* logic set up the right #define values for arm_math.h
*/
#include <zephyr/kernel.h>
#include <arm_math.h>
#include "dsplib.h"
static inline void zdsp_mult_q7(const DSP_DATA q7_t *src_a, const DSP_DATA q7_t *src_b,
DSP_DATA q7_t *dst, uint32_t block_size)
{
dsp_mult_q7(src_a, src_b, dst, block_size);
}
static inline void zdsp_mult_q15(const DSP_DATA q15_t *src_a, const DSP_DATA q15_t *src_b,
DSP_DATA q15_t *dst, uint32_t block_size)
{
dsp_mult_q15(src_a, src_b, dst, block_size);
}
static inline void zdsp_mult_q31(const DSP_DATA q31_t *src_a, const DSP_DATA q31_t *src_b,
DSP_DATA q31_t *dst, uint32_t block_size)
{
dsp_mult_q31(src_a, src_b, dst, block_size);
}
static inline void zdsp_mult_f32(const DSP_DATA float32_t *src_a, const DSP_DATA float32_t *src_b,
DSP_DATA float32_t *dst, uint32_t block_size)
{
dsp_mult_f32(src_a, src_b, dst, block_size);
}
static inline void zdsp_add_q7(const DSP_DATA q7_t *src_a, const DSP_DATA q7_t *src_b,
DSP_DATA q7_t *dst, uint32_t block_size)
{
dsp_add_q7(src_a, src_b, dst, block_size);
}
static inline void zdsp_add_q15(const DSP_DATA q15_t *src_a, const DSP_DATA q15_t *src_b,
DSP_DATA q15_t *dst, uint32_t block_size)
{
dsp_add_q15(src_a, src_b, dst, block_size);
}
static inline void zdsp_add_q31(const DSP_DATA q31_t *src_a, const DSP_DATA q31_t *src_b,
DSP_DATA q31_t *dst, uint32_t block_size)
{
dsp_add_q31(src_a, src_b, dst, block_size);
}
static inline void zdsp_add_f32(const DSP_DATA float32_t *src_a, const DSP_DATA float32_t *src_b,
DSP_DATA float32_t *dst, uint32_t block_size)
{
dsp_add_f32(src_a, src_b, dst, block_size);
}
static inline void zdsp_sub_q7(const DSP_DATA q7_t *src_a, const DSP_DATA q7_t *src_b,
DSP_DATA q7_t *dst, uint32_t block_size)
{
dsp_sub_q7(src_a, src_b, dst, block_size);
}
static inline void zdsp_sub_q15(const DSP_DATA q15_t *src_a, const DSP_DATA q15_t *src_b,
DSP_DATA q15_t *dst, uint32_t block_size)
{
dsp_sub_q15(src_a, src_b, dst, block_size);
}
static inline void zdsp_sub_q31(const DSP_DATA q31_t *src_a, const DSP_DATA q31_t *src_b,
DSP_DATA q31_t *dst, uint32_t block_size)
{
dsp_sub_q31(src_a, src_b, dst, block_size);
}
static inline void zdsp_sub_f32(const DSP_DATA float32_t *src_a, const DSP_DATA float32_t *src_b,
DSP_DATA float32_t *dst, uint32_t block_size)
{
dsp_sub_f32(src_a, src_b, dst, block_size);
}
static inline void zdsp_scale_q7(const DSP_DATA q7_t *src, q7_t scale_fract, int8_t shift,
DSP_DATA q7_t *dst, uint32_t block_size)
{
dsp_scale_q7(src, scale_fract, shift, dst, block_size);
}
static inline void zdsp_scale_q15(const DSP_DATA q15_t *src, q15_t scale_fract, int8_t shift,
DSP_DATA q15_t *dst, uint32_t block_size)
{
dsp_scale_q15(src, scale_fract, shift, dst, block_size);
}
static inline void zdsp_scale_q31(const DSP_DATA q31_t *src, q31_t scale_fract, int8_t shift,
DSP_DATA q31_t *dst, uint32_t block_size)
{
dsp_scale_q31(src, scale_fract, shift, dst, block_size);
}
static inline void zdsp_scale_f32(const DSP_DATA float32_t *src, float32_t scale,
DSP_DATA float32_t *dst, uint32_t block_size)
{
dsp_scale_f32(src, scale, dst, block_size);
}
static inline void zdsp_abs_q7(const DSP_DATA q7_t *src, DSP_DATA q7_t *dst, uint32_t block_size)
{
dsp_abs_q7(src, dst, block_size);
}
static inline void zdsp_abs_q15(const DSP_DATA q15_t *src, DSP_DATA q15_t *dst, uint32_t block_size)
{
dsp_abs_q15(src, dst, block_size);
}
static inline void zdsp_abs_q31(const DSP_DATA q31_t *src, DSP_DATA q31_t *dst, uint32_t block_size)
{
dsp_abs_q31(src, dst, block_size);
}
static inline void zdsp_abs_f32(const DSP_DATA float32_t *src, DSP_DATA float32_t *dst,
uint32_t block_size)
{
dsp_abs_f32(src, dst, block_size);
}
static inline void zdsp_negate_q7(const DSP_DATA q7_t *src, DSP_DATA q7_t *dst, uint32_t block_size)
{
dsp_negate_q7(src, dst, block_size);
}
static inline void zdsp_negate_q15(const DSP_DATA q15_t *src, DSP_DATA q15_t *dst,
uint32_t block_size)
{
dsp_negate_q15(src, dst, block_size);
}
static inline void zdsp_negate_q31(const DSP_DATA q31_t *src, DSP_DATA q31_t *dst,
uint32_t block_size)
{
dsp_negate_q31(src, dst, block_size);
}
static inline void zdsp_negate_f32(const DSP_DATA float32_t *src, DSP_DATA float32_t *dst,
uint32_t block_size)
{
dsp_negate_f32(src, dst, block_size);
}
static inline void zdsp_dot_prod_q7(const DSP_DATA q7_t *src_a, const DSP_DATA q7_t *src_b,
uint32_t block_size, DSP_DATA q31_t *dst)
{
dsp_dot_prod_q7(src_a, src_b, block_size, dst);
}
static inline void zdsp_dot_prod_q15(const DSP_DATA q15_t *src_a, const DSP_DATA q15_t *src_b,
uint32_t block_size, DSP_DATA q63_t *dst)
{
dsp_dot_prod_q15(src_a, src_b, block_size, dst);
}
static inline void zdsp_dot_prod_q31(const DSP_DATA q31_t *src_a, const DSP_DATA q31_t *src_b,
uint32_t block_size, DSP_DATA q63_t *dst)
{
dsp_dot_prod_q31(src_a, src_b, block_size, dst);
}
static inline void zdsp_dot_prod_f32(const DSP_DATA float32_t *src_a,
const DSP_DATA float32_t *src_b, uint32_t block_size,
DSP_DATA float32_t *dst)
{
dsp_dot_prod_f32(src_a, src_b, block_size, dst);
}
static inline void zdsp_shift_q7(const DSP_DATA q7_t *src, int8_t shift_bits, DSP_DATA q7_t *dst,
uint32_t block_size)
{
dsp_shift_q7(src, shift_bits, dst, block_size);
}
static inline void zdsp_shift_q15(const DSP_DATA q15_t *src, int8_t shift_bits, DSP_DATA q15_t *dst,
uint32_t block_size)
{
dsp_shift_q15(src, shift_bits, dst, block_size);
}
static inline void zdsp_shift_q31(const DSP_DATA q31_t *src, int8_t shift_bits, DSP_DATA q31_t *dst,
uint32_t block_size)
{
dsp_shift_q31(src, shift_bits, dst, block_size);
}
static inline void zdsp_offset_q7(const DSP_DATA q7_t *src, q7_t offset, DSP_DATA q7_t *dst,
uint32_t block_size)
{
dsp_offset_q7(src, offset, dst, block_size);
}
static inline void zdsp_offset_q15(const DSP_DATA q15_t *src, q15_t offset, DSP_DATA q15_t *dst,
uint32_t block_size)
{
dsp_offset_q15(src, offset, dst, block_size);
}
static inline void zdsp_offset_q31(const DSP_DATA q31_t *src, q31_t offset, DSP_DATA q31_t *dst,
uint32_t block_size)
{
dsp_offset_q31(src, offset, dst, block_size);
}
static inline void zdsp_offset_f32(const DSP_DATA float32_t *src, float32_t offset,
DSP_DATA float32_t *dst, uint32_t block_size)
{
dsp_offset_f32(src, offset, dst, block_size);
}
static inline void zdsp_clip_q7(const DSP_DATA q7_t *src, DSP_DATA q7_t *dst, q7_t low, q7_t high,
uint32_t num_samples)
{
arm_clip_q7(src, dst, low, high, num_samples);
}
static inline void zdsp_clip_q15(const DSP_DATA q15_t *src, DSP_DATA q15_t *dst, q15_t low,
q15_t high, uint32_t num_samples)
{
arm_clip_q15(src, dst, low, high, num_samples);
}
static inline void zdsp_clip_q31(const DSP_DATA q31_t *src, DSP_DATA q31_t *dst, q31_t low,
q31_t high, uint32_t num_samples)
{
arm_clip_q31(src, dst, low, high, num_samples);
}
static inline void zdsp_clip_f32(const DSP_DATA float32_t *src, DSP_DATA float32_t *dst,
float32_t low, float32_t high, uint32_t num_samples)
{
arm_clip_f32(src, dst, low, high, num_samples);
}
static inline void zdsp_and_u8(const DSP_DATA uint8_t *src_a, const DSP_DATA uint8_t *src_b,
DSP_DATA uint8_t *dst, uint32_t block_size)
{
arm_and_u8(src_a, src_b, dst, block_size);
}
static inline void zdsp_and_u16(const DSP_DATA uint16_t *src_a, const DSP_DATA uint16_t *src_b,
DSP_DATA uint16_t *dst, uint32_t block_size)
{
arm_and_u16(src_a, src_b, dst, block_size);
}
static inline void zdsp_and_u32(const DSP_DATA uint32_t *src_a, const DSP_DATA uint32_t *src_b,
DSP_DATA uint32_t *dst, uint32_t block_size)
{
arm_and_u32(src_a, src_b, dst, block_size);
}
static inline void zdsp_or_u8(const DSP_DATA uint8_t *src_a, const DSP_DATA uint8_t *src_b,
DSP_DATA uint8_t *dst, uint32_t block_size)
{
arm_or_u8(src_a, src_b, dst, block_size);
}
static inline void zdsp_or_u16(const DSP_DATA uint16_t *src_a, const DSP_DATA uint16_t *src_b,
DSP_DATA uint16_t *dst, uint32_t block_size)
{
arm_or_u16(src_a, src_b, dst, block_size);
}
static inline void zdsp_or_u32(const DSP_DATA uint32_t *src_a, const DSP_DATA uint32_t *src_b,
DSP_DATA uint32_t *dst, uint32_t block_size)
{
arm_or_u32(src_a, src_b, dst, block_size);
}
static inline void zdsp_xor_u8(const DSP_DATA uint8_t *src_a, const DSP_DATA uint8_t *src_b,
DSP_DATA uint8_t *dst, uint32_t block_size)
{
arm_xor_u8(src_a, src_b, dst, block_size);
}
static inline void zdsp_xor_u16(const DSP_DATA uint16_t *src_a, const DSP_DATA uint16_t *src_b,
DSP_DATA uint16_t *dst, uint32_t block_size)
{
arm_xor_u16(src_a, src_b, dst, block_size);
}
static inline void zdsp_xor_u32(const DSP_DATA uint32_t *src_a, const DSP_DATA uint32_t *src_b,
DSP_DATA uint32_t *dst, uint32_t block_size)
{
arm_xor_u32(src_a, src_b, dst, block_size);
}
static inline void zdsp_not_u8(const DSP_DATA uint8_t *src, DSP_DATA uint8_t *dst,
uint32_t block_size)
{
arm_not_u8(src, dst, block_size);
}
static inline void zdsp_not_u16(const DSP_DATA uint16_t *src, DSP_DATA uint16_t *dst,
uint32_t block_size)
{
arm_not_u16(src, dst, block_size);
}
static inline void zdsp_not_u32(const DSP_DATA uint32_t *src, DSP_DATA uint32_t *dst,
uint32_t block_size)
{
arm_not_u32(src, dst, block_size);
}
#ifdef __cplusplus
}
#endif
#endif /* SUBSYS_MATH_ARC_BACKEND_PUBLIC_ZDSP_BACKEND_DSP_H_ */

View file

@ -14,3 +14,8 @@ target_sources(app PRIVATE
target_sources_ifdef(CONFIG_FP16 app PRIVATE src/f16.c) target_sources_ifdef(CONFIG_FP16 app PRIVATE src/f16.c)
target_include_directories(app PRIVATE ${ZEPHYR_BASE}/tests/lib/cmsis_dsp) target_include_directories(app PRIVATE ${ZEPHYR_BASE}/tests/lib/cmsis_dsp)
if(COMPILER STREQUAL arcmwdt)
get_property(Z_ARC_DSP_OPTIONS GLOBAL PROPERTY z_arc_dsp_options)
target_compile_options(app PRIVATE ${Z_ARC_DSP_OPTIONS})
endif()

View file

@ -0,0 +1,8 @@
CONFIG_ZTEST=y
CONFIG_ZTEST_NEW_API=y
CONFIG_ARCMWDT_LIBC=y
CONFIG_CPLUSPLUS=y
CONFIG_DSP=y
CONFIG_CMSIS_DSP=y
CONFIG_CMSIS_DSP_BASICMATH=y
CONFIG_DSP_BACKEND_ARCMWDT=y

View file

@ -19,3 +19,8 @@ tests:
- CONFIG_FPU=y - CONFIG_FPU=y
min_flash: 128 min_flash: 128
min_ram: 64 min_ram: 64
zdsp.basicmath.arcmwdt:
filter: CONFIG_ISA_ARCV2
toolchain_allow: arcmwdt
platform_allow: nsim_em11d
extra_args: CONF_FILE=prj_arc.conf