From 537c71cb602871b9957eeb07bca4d5740a2e7eb4 Mon Sep 17 00:00:00 2001 From: Kristofer Jonsson Date: Tue, 5 May 2020 14:17:22 +0200 Subject: MLBEDSW-2194 Updating PMU files Moving PMU files from ethosu_pmu to include and src. Adding extern "C" to PMU header. Removing CMake generated file. Updating default path to CMSIS. Removing timing adapter. Change-Id: I4834c5361c14efe629c5cb36a17013d02cc765c8 --- CMakeLists.txt | 51 +++-- ethosu_pmu/CMakeLists.txt | 39 ---- ethosu_pmu/common.h | 50 ----- ethosu_pmu/driver.c | 82 ------- ethosu_pmu/ethosu_pmu_config.h.in | 34 --- ethosu_pmu/include/pmu_ethosu.h | 458 -------------------------------------- include/pmu_ethosu.h | 429 +++++++++++++++++++++++++++++++++++ src/ethosu_pmu.c | 102 +++++++++ 8 files changed, 558 insertions(+), 687 deletions(-) delete mode 100644 ethosu_pmu/CMakeLists.txt delete mode 100644 ethosu_pmu/common.h delete mode 100644 ethosu_pmu/driver.c delete mode 100644 ethosu_pmu/ethosu_pmu_config.h.in delete mode 100644 ethosu_pmu/include/pmu_ethosu.h create mode 100644 include/pmu_ethosu.h create mode 100644 src/ethosu_pmu.c diff --git a/CMakeLists.txt b/CMakeLists.txt index d53662d..6e9d80e 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -24,17 +24,10 @@ project(ethosu_core_driver VERSION 0.0.1) # Build options # -option(DRIVER_BUILD_PMU "Driver supports NPU-PMU" ON) +option(DRIVER_PMU_AUTOINIT "Enable PMU boot auto-initialization" OFF) option(LOG_SUPPORT "Enable logging." ON) -set(CMSIS_PATH "${CMAKE_CURRENT_SOURCE_DIR}/../library/cmsis" CACHE PATH "Path to CMSIS.") -set(TIMING_ADAPTER_PATH "${CMAKE_CURRENT_SOURCE_DIR}/timing-adapter" CACHE STRING "Path to timing adapter.") - -if(EXISTS "${TIMING_ADAPTER_PATH}") - option(DRIVER_BUILD_TIMING_ADAPTER "Enable timing-adapter" ON) -else() - option(DRIVER_BUILD_TIMING_ADAPTER "Enable timing-adapter" OFF) -endif() +set(CMSIS_PATH "${CMAKE_CURRENT_SOURCE_DIR}/../cmsis" CACHE PATH "Path to CMSIS.") # # Global settings @@ -74,20 +67,33 @@ include_directories(${CMSIS_PATH}/CMSIS/Core/Include) # Build driver library add_library(ethosu_core_driver STATIC) -target_include_directories(ethosu_core_driver - PUBLIC include) -target_sources(ethosu_core_driver PRIVATE src/ethosu_driver.c src/ethosu_device.c) - -# Build timing adapter -if (DRIVER_BUILD_TIMING_ADAPTER) - add_subdirectory(timing-adapter) - target_link_libraries(ethosu_core_driver PUBLIC timing-adapter) -endif() +target_include_directories(ethosu_core_driver PUBLIC include) +target_sources(ethosu_core_driver PRIVATE src/ethosu_driver.c src/ethosu_device.c src/ethosu_pmu.c) # Build PMU -if (DRIVER_BUILD_PMU) - add_subdirectory(ethosu_pmu) - target_link_libraries(ethosu_core_driver PUBLIC ethosu_core_driver_pmu) +if (DRIVER_PMU_AUTOINIT) + set(NPU_PMCR "0x0" CACHE STRING "Register control b0 = CNT_EN = Enable counters (RW), b1 = EVENT_CNT_RST = Reset event counters (WO), b2 = CYCLE_CNT_RST = Reset cycle counter (WO), b[15:11] = Number of event counters (RO)") + set(NPU_PMCNTENSET "0x0" CACHE STRING "Bit k enables event counter k. k=31 enables the cycle counter. Read value is current status.") + set(NPU_PMCNTENCLR "0x0" CACHE STRING "Bit k disables event counter k. k=31 disables the cycle counter. Reda value is current status.") + set(NPU_PMOVSSET "0x0" CACHE STRING "Overflow detection set. Bit k is for counter k. k=31 is cycle counter.") + set(NPU_PMOVSCLR "0x0" CACHE STRING "Overflow detection clear. Bit k is for counter k. k=31 is cycle counter.") + set(NPU_PMINTSET "0x0" CACHE STRING "Interrupt set. Bit k is for counter k. k=31 is cycle counter.") + set(NPU_PMINTCLR "0x8003" CACHE STRING "Interrupt clear. Bit k is for counter k. k=31 is cycle counter.") + set(NPU_PMCCNTR "0x0" CACHE STRING "Cycle counter, 48 bits value") + set(NPU_PMCCNTR_CFG "0x0" CACHE STRING "b[9:0] Start Event – this event number starts the cycle counter b[25:16] Stop Event – this event number stops the cycle counter") + + target_compile_definitions(ethosu_core_driver PRIVATE + PMU_AUTOINIT + INIT_PMCR=${NPU_PMCR} + INIT_PMCNTENSET=${NPU_PMCNTENSET} + INIT_PMCNTENCLR=${NPU_PMCNTENCLR} + INIT_PMOVSSET=${NPU_PMOVSSET} + INIT_PMOVSCLR=${NPU_PMOVSCLR} + INIT_PMINTSET=${NPU_PMINTSET} + INIT_PMINTCLR=${NPU_PMINTCLR} + INIT_PMCCNTR=${NPU_PMCCNTR} + INIT_PMCCNTR_CFG=${NPU_PMCCNTR_CFG} + ) endif() # @@ -97,9 +103,6 @@ endif() message(STATUS "*******************************************************") message(STATUS "PROJECT_NAME : ${PROJECT_NAME}") message(STATUS "CMAKE_SYSTEM_PROCESSOR : ${CMAKE_SYSTEM_PROCESSOR}") -message(STATUS "DRIVER_BUILD_PMU : ${DRIVER_BUILD_PMU}") -message(STATUS "DRIVER_BUILD_TIMING_ADAPTER : ${DRIVER_BUILD_TIMING_ADAPTER}") message(STATUS "LOG_SUPPORT : ${LOG_SUPPORT}") message(STATUS "CMSIS_PATH : ${CMSIS_PATH}") -message(STATUS "TIMING_ADAPTER_PATH : ${TIMING_ADAPTER_PATH}") message(STATUS "*******************************************************") diff --git a/ethosu_pmu/CMakeLists.txt b/ethosu_pmu/CMakeLists.txt deleted file mode 100644 index 98c403e..0000000 --- a/ethosu_pmu/CMakeLists.txt +++ /dev/null @@ -1,39 +0,0 @@ -# Copyright (c) 2019-2020 Arm Limited. All rights reserved. -# -# SPDX-License-Identifier: Apache-2.0 -# -# Licensed under the Apache License, Version 2.0 (the License); you may -# not use this file except in compliance with the License. -# You may obtain a copy of the License at -# -# www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an AS IS BASIS, WITHOUT -# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. -# - -# -# Global options -# - -set(NPU_PMCR "0x0" CACHE STRING "Register control b0 = CNT_EN = Enable counters (RW), b1 = EVENT_CNT_RST = Reset event counters (WO), b2 = CYCLE_CNT_RST = Reset cycle counter (WO), b[15:11] = Number of event counters (RO)") -set(NPU_PMCNTENSET "0x0" CACHE STRING "Bit k enables event counter k. k=31 enables the cycle counter. Read value is current status.") -set(NPU_PMCNTENCLR "0x0" CACHE STRING "Bit k disables event counter k. k=31 disables the cycle counter. Reda value is current status.") -set(NPU_PMOVSSET "0x0" CACHE STRING "Overflow detection set. Bit k is for counter k. k=31 is cycle counter.") -set(NPU_PMOVSCLR "0x0" CACHE STRING "Overflow detection clear. Bit k is for counter k. k=31 is cycle counter.") -set(NPU_PMINTSET "0x0" CACHE STRING "Interrupt set. Bit k is for counter k. k=31 is cycle counter.") -set(NPU_PMINTCLR "0x8003" CACHE STRING "Interrupt clear. Bit k is for counter k. k=31 is cycle counter.") -set(NPU_PMCCNTR "0x0" CACHE STRING "Cycle counter, 48 bits value") -set(NPU_PMCCNTR_CFG "0x0" CACHE STRING "b[9:0] Start Event – this event number starts the cycle counter b[25:16] Stop Event – this event number stops the cycle counter") - -# -# Build binaries -# - -add_library(ethosu_core_driver_pmu STATIC driver.c) -target_include_directories(ethosu_core_driver_pmu PUBLIC include PRIVATE ${CMAKE_CURRENT_BINARY_DIR}) - -configure_file("${CMAKE_CURRENT_SOURCE_DIR}/ethosu_pmu_config.h.in" "${CMAKE_CURRENT_BINARY_DIR}/ethosu_pmu_config.h") diff --git a/ethosu_pmu/common.h b/ethosu_pmu/common.h deleted file mode 100644 index 6b481a6..0000000 --- a/ethosu_pmu/common.h +++ /dev/null @@ -1,50 +0,0 @@ -/* - * Copyright (c) 2019-2020 Arm Limited. All rights reserved. - * - * SPDX-License-Identifier: Apache-2.0 - * - * Licensed under the Apache License, Version 2.0 (the License); you may - * not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an AS IS BASIS, WITHOUT - * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -#ifndef ethosu_pmu_common_h -#define ethosu_pmu_common_h - -#include - -/* Separators for EXPAND_(name) macros */ -#define COMMA , -#define SEMICOLON ; -#define COLON : -#define NOTHING - -#if defined(CPU_CORTEX_M55) -#define NPU_BASE ((uint32_t)0x41700000) -#else -#define NPU_BASE ((uint32_t)0x41105000) -#endif - -#define ETHOSU_PMU_CTRL_BASE (NPU_BASE + ((uint32_t)0x180)) -#define ETHOSU_PMU_CNTR_BASE (NPU_BASE + ((uint32_t)0x300)) -#define ETHOSU_PMU_EVNT_BASE (NPU_BASE + ((uint32_t)0x380)) - -#define __init __attribute__((constructor)) -#define __exit __attribute__((destructor)) - -#ifdef NEVER -#define INIT __init void -#define EXIT __exit void -#else -#define INIT static __init void -#define EXIT static __init void -#endif - -#endif // ethosu_pmu_common_h diff --git a/ethosu_pmu/driver.c b/ethosu_pmu/driver.c deleted file mode 100644 index 80cd79a..0000000 --- a/ethosu_pmu/driver.c +++ /dev/null @@ -1,82 +0,0 @@ -/* - * Copyright (c) 2019-2020 Arm Limited. All rights reserved. - * - * SPDX-License-Identifier: Apache-2.0 - * - * Licensed under the Apache License, Version 2.0 (the License); you may - * not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an AS IS BASIS, WITHOUT - * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -#include "common.h" -#include "ethosu55_interface.h" -#include "ethosu_pmu_config.h" -#include -#include -#include -#include - -PMU_Ethosu_ctrl_Type *ethosu_pmu_ctrl = (PMU_Ethosu_ctrl_Type *)ETHOSU_PMU_CTRL_BASE; -PMU_Ethosu_cntr_Type *ethosu_pmu_cntr = (PMU_Ethosu_cntr_Type *)ETHOSU_PMU_CNTR_BASE; -PMU_Ethosu_evnt_Type *ethosu_pmu_evnt = (PMU_Ethosu_evnt_Type *)ETHOSU_PMU_EVNT_BASE; - -// Local functions & macros -#define PMUREG0(NAME) INIT_##NAME - -#define ETHOSU_PMU_INIT(N) \ - *ethosu_pmu_ctrl = (PMU_Ethosu_ctrl_Type){.PMCR = PMUREG##N(PMCR), \ - .PMCNTENSET = PMUREG##N(PMCNTENSET), \ - .PMCNTENCLR = PMUREG##N(PMCNTENCLR), \ - .PMOVSSET = PMUREG##N(PMOVSSET), \ - .PMOVSCLR = PMUREG##N(PMOVSCLR), \ - .PMINTSET = PMUREG##N(PMINTSET), \ - .PMINTCLR = PMUREG##N(PMINTCLR), \ - .PMCCNTR = PMUREG##N(PMCCNTR), \ - .PMCCNTR_CFG = PMUREG##N(PMCCNTR_CFG)}; - -// Public interfaces - -#define EVTYPE(A, name) \ - case PMU_EVENT_TYPE_##name: \ - return ETHOSU_PMU_##name -enum ethosu_pmu_event_type pmu_event_type(uint32_t id) -{ - switch (id) - { - EXPAND_PMU_EVENT_TYPE(EVTYPE, SEMICOLON); - } - return ETHOSU_PMU_SENTINEL; -} - -#define EVID(A, name) (PMU_EVENT_TYPE_##name) -static const enum pmu_event_type eventbyid[] = {EXPAND_PMU_EVENT_TYPE(EVID, COMMA)}; -uint32_t pmu_event_value(enum ethosu_pmu_event_type event) -{ - if (!(event < ETHOSU_PMU_SENTINEL) || (event < 0)) - { - return (uint32_t)(-1); - } - - return eventbyid[event]; -} - -// Driver Init/exit functions -INIT ethosu_pmu_driver_init(void) -{ - ETHOSU_PMU_INIT(0) - - for (int i = 0; i < ETHOSU_PMU_NCOUNTERS; i++) - { - *ethosu_pmu_cntr[i] = 0; - *ethosu_pmu_evnt[i] = 0; - } -} - -EXIT ethosu_pmu_driver_exit(void) {} diff --git a/ethosu_pmu/ethosu_pmu_config.h.in b/ethosu_pmu/ethosu_pmu_config.h.in deleted file mode 100644 index 05ca476..0000000 --- a/ethosu_pmu/ethosu_pmu_config.h.in +++ /dev/null @@ -1,34 +0,0 @@ -/* - * Copyright (c) 2019-2020 Arm Limited. All rights reserved. - * - * SPDX-License-Identifier: Apache-2.0 - * - * Licensed under the Apache License, Version 2.0 (the License); you may - * not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an AS IS BASIS, WITHOUT - * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -/* ETHOSU_PMU config file */ -#ifndef ethosu_pmu_config_h -#define ethosu_pmu_config_h - -/* Initial values */ -#define INIT_PMCR (@NPU_PMCR@) -#define INIT_PMCNTENSET (@NPU_PMCNTENSET@) -#define INIT_PMCNTENCLR (@NPU_PMCNTENCLR@) -#define INIT_PMOVSSET (@NPU_PMOVSSET@) -#define INIT_PMOVSCLR (@NPU_PMOVSCLR@) -#define INIT_PMINTSET (@NPU_PMINTSET@) -#define INIT_PMINTCLR (@NPU_PMINTCLR@) -#define INIT_PMCCNTR (@NPU_PMCCNTR@) -#define INIT_PMCCNTR_CFG (@NPU_PMCCNTR_CFG@) - -#endif diff --git a/ethosu_pmu/include/pmu_ethosu.h b/ethosu_pmu/include/pmu_ethosu.h deleted file mode 100644 index e5eaba9..0000000 --- a/ethosu_pmu/include/pmu_ethosu.h +++ /dev/null @@ -1,458 +0,0 @@ -/* - * Copyright (c) 2019-2020 Arm Limited. All rights reserved. - * - * SPDX-License-Identifier: Apache-2.0 - * - * Licensed under the Apache License, Version 2.0 (the License); you may - * not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an AS IS BASIS, WITHOUT - * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#if defined(__ICCARM__) -#pragma system_include /* treat file as system include file for MISRA check */ -#elif defined(__clang__) -#pragma clang system_header /* treat file as system include file */ -#endif - -#ifndef PMU_ETHOSU_H -#define PMU_ETHOSU_H - -#define ETHOSU_PMU_NCOUNTERS 4 - -#include - -#ifdef NOTNOW -#if defined(CPU_CORTEX_M55) -#include -#elif defined(CPU_CORTEX_M33) -#include -#else -#error npu-pmu not supported for CPU -#endif -#else -/* IO definitions (access restrictions to peripheral registers) */ -/** - \defgroup CMSIS_glob_defs CMSIS Global Defines - - IO Type Qualifiers are used - \li to specify the access to peripheral variables. - \li for automatic generation of peripheral register debug information. -*/ -#ifdef __cplusplus -#define __I volatile /*!< Defines 'read only' permissions */ -#else -#define __I volatile const /*!< Defines 'read only' permissions */ -#endif -#define __O volatile /*!< Defines 'write only' permissions */ -#define __IO volatile /*!< Defines 'read / write' permissions */ - -/* following defines should be used for structure members */ -#define __IM volatile const /*! Defines 'read only' structure member permissions */ -#define __OM volatile /*! Defines 'write only' structure member permissions */ -#define __IOM volatile /*! Defines 'read / write' structure member permissions */ -#endif - -typedef struct -{ - __IOM uint32_t PMCR; - __IOM uint32_t PMCNTENSET; - __IOM uint32_t PMCNTENCLR; - __IOM uint32_t PMOVSSET; - __IOM uint32_t PMOVSCLR; - __IOM uint32_t PMINTSET; - __IOM uint32_t PMINTCLR; - __IOM uint64_t PMCCNTR; - __IOM uint32_t PMCCNTR_CFG; -} PMU_Ethosu_ctrl_Type; - -typedef uint32_t PMU_Ethosu_cntr_Type[ETHOSU_PMU_NCOUNTERS]; -typedef uint32_t PMU_Ethosu_evnt_Type[ETHOSU_PMU_NCOUNTERS]; - -/** \brief HW Supported ETHOSU PMU Events - * - * Note: These values are symbolic. Actual HW-values may change. I.e. always use API - * to set/get actual event-type value. - * */ -enum ethosu_pmu_event_type -{ - ETHOSU_PMU_NO_EVENT = 0, - ETHOSU_PMU_CYCLE, - ETHOSU_PMU_NPU_IDLE, - ETHOSU_PMU_MAC_ACTIVE, - ETHOSU_PMU_MAC_ACTIVE_8BIT, - ETHOSU_PMU_MAC_ACTIVE_16BIT, - ETHOSU_PMU_MAC_DPU_ACTIVE, - ETHOSU_PMU_MAC_STALLED_BY_WD_ACC, - ETHOSU_PMU_MAC_STALLED_BY_WD, - ETHOSU_PMU_MAC_STALLED_BY_ACC, - ETHOSU_PMU_MAC_STALLED_BY_IB, - ETHOSU_PMU_MAC_ACTIVE_32BIT, - ETHOSU_PMU_AO_ACTIVE, - ETHOSU_PMU_AO_ACTIVE_8BIT, - ETHOSU_PMU_AO_ACTIVE_16BIT, - ETHOSU_PMU_AO_STALLED_BY_OFMP_OB, - ETHOSU_PMU_AO_STALLED_BY_OFMP, - ETHOSU_PMU_AO_STALLED_BY_OB, - ETHOSU_PMU_AO_STALLED_BY_ACC_IB, - ETHOSU_PMU_AO_STALLED_BY_ACC, - ETHOSU_PMU_AO_STALLED_BY_IB, - ETHOSU_PMU_WD_ACTIVE, - ETHOSU_PMU_WD_STALLED, - ETHOSU_PMU_WD_STALLED_BY_WS, - ETHOSU_PMU_WD_STALLED_BY_WD_BUF, - ETHOSU_PMU_WD_PARSE_ACTIVE, - ETHOSU_PMU_WD_PARSE_STALLED, - ETHOSU_PMU_WD_PARSE_STALLED_IN, - ETHOSU_PMU_WD_PARSE_STALLED_OUT, - ETHOSU_PMU_WD_TRANS_WS, - ETHOSU_PMU_WD_TRANS_WB, - ETHOSU_PMU_WD_TRANS_DW0, - ETHOSU_PMU_WD_TRANS_DW1, - ETHOSU_PMU_AXI0_RD_TRANS_ACCEPTED, - ETHOSU_PMU_AXI0_RD_TRANS_COMPLETED, - ETHOSU_PMU_AXI0_RD_DATA_BEAT_RECEIVED, - ETHOSU_PMU_AXI0_RD_TRAN_REQ_STALLED, - ETHOSU_PMU_AXI0_WR_TRANS_ACCEPTED, - ETHOSU_PMU_AXI0_WR_TRANS_COMPLETED_M, - ETHOSU_PMU_AXI0_WR_TRANS_COMPLETED_S, - ETHOSU_PMU_AXI0_WR_DATA_BEAT_WRITTEN, - ETHOSU_PMU_AXI0_WR_TRAN_REQ_STALLED, - ETHOSU_PMU_AXI0_WR_DATA_BEAT_STALLED, - ETHOSU_PMU_AXI0_ENABLED_CYCLES, - ETHOSU_PMU_AXI0_RD_STALL_LIMIT, - ETHOSU_PMU_AXI0_WR_STALL_LIMIT, - ETHOSU_PMU_AXI1_RD_TRANS_ACCEPTED, - ETHOSU_PMU_AXI1_RD_TRANS_COMPLETED, - ETHOSU_PMU_AXI1_RD_DATA_BEAT_RECEIVED, - ETHOSU_PMU_AXI1_RD_TRAN_REQ_STALLED, - ETHOSU_PMU_AXI1_WR_TRANS_ACCEPTED, - ETHOSU_PMU_AXI1_WR_TRANS_COMPLETED_M, - ETHOSU_PMU_AXI1_WR_TRANS_COMPLETED_S, - ETHOSU_PMU_AXI1_WR_DATA_BEAT_WRITTEN, - ETHOSU_PMU_AXI1_WR_TRAN_REQ_STALLED, - ETHOSU_PMU_AXI1_WR_DATA_BEAT_STALLED, - ETHOSU_PMU_AXI1_ENABLED_CYCLES, - ETHOSU_PMU_AXI1_RD_STALL_LIMIT, - ETHOSU_PMU_AXI1_WR_STALL_LIMIT, - ETHOSU_PMU_AXI_LATENCY_ANY, - ETHOSU_PMU_AXI_LATENCY_32, - ETHOSU_PMU_AXI_LATENCY_64, - ETHOSU_PMU_AXI_LATENCY_128, - ETHOSU_PMU_AXI_LATENCY_256, - ETHOSU_PMU_AXI_LATENCY_512, - ETHOSU_PMU_AXI_LATENCY_1024, - - ETHOSU_PMU_SENTINEL // End-marker (not event) -}; - -extern PMU_Ethosu_ctrl_Type *ethosu_pmu_ctrl; -extern PMU_Ethosu_cntr_Type *ethosu_pmu_cntr; -extern PMU_Ethosu_evnt_Type *ethosu_pmu_evnt; - -#define ETHOSU_PMU_CTRL_ENABLE_Msk (0x0001) -#define ETHOSU_PMU_CTRL_EVENTCNT_RESET_Msk (0x0002) -#define ETHOSU_PMU_CTRL_CYCCNT_RESET_Msk (0x0004) -#define ETHOSU_PMU_CNT1_Msk (1UL << 0) -#define ETHOSU_PMU_CNT2_Msk (1UL << 1) -#define ETHOSU_PMU_CNT3_Msk (1UL << 2) -#define ETHOSU_PMU_CNT4_Msk (1UL << 3) -#define ETHOSU_PMU_CCNT_Msk (1UL << 31) - -/* Transpose functions between HW-event-type and event-id*/ -enum ethosu_pmu_event_type pmu_event_type(uint32_t); -uint32_t pmu_event_value(enum ethosu_pmu_event_type); - -// CMSIS ref API -/** \brief PMU Functions */ - -__STATIC_INLINE void ETHOSU_PMU_Enable(void); -__STATIC_INLINE void ETHOSU_PMU_Disable(void); - -__STATIC_INLINE void ETHOSU_PMU_Set_EVTYPER(uint32_t num, enum ethosu_pmu_event_type type); -__STATIC_INLINE enum ethosu_pmu_event_type ETHOSU_PMU_Get_EVTYPER(uint32_t num); - -__STATIC_INLINE void ETHOSU_PMU_CYCCNT_Reset(void); -__STATIC_INLINE void ETHOSU_PMU_EVCNTR_ALL_Reset(void); - -__STATIC_INLINE void ETHOSU_PMU_CNTR_Enable(uint32_t mask); -__STATIC_INLINE void ETHOSU_PMU_CNTR_Disable(uint32_t mask); -__STATIC_INLINE uint32_t ETHOSU_PMU_CNTR_Status(); - -__STATIC_INLINE uint64_t ETHOSU_PMU_Get_CCNTR(void); -__STATIC_INLINE void ETHOSU_PMU_Set_CCNTR(uint64_t val); -__STATIC_INLINE uint32_t ETHOSU_PMU_Get_EVCNTR(uint32_t num); -__STATIC_INLINE void ETHOSU_PMU_Set_EVCNTR(uint32_t num, uint32_t val); - -__STATIC_INLINE uint32_t ETHOSU_PMU_Get_CNTR_OVS(void); -__STATIC_INLINE void ETHOSU_PMU_Set_CNTR_OVS(uint32_t mask); - -__STATIC_INLINE void ETHOSU_PMU_Set_CNTR_IRQ_Enable(uint32_t mask); -__STATIC_INLINE void ETHOSU_PMU_Set_CNTR_IRQ_Disable(uint32_t mask); -__STATIC_INLINE uint32_t ETHOSU_PMU_Get_IRQ_Enable(); - -__STATIC_INLINE void ETHOSU_PMU_CNTR_Increment(uint32_t mask); - -/** - \brief Enable the PMU -*/ -__STATIC_INLINE void ETHOSU_PMU_Enable(void) -{ - ethosu_pmu_ctrl->PMCR |= ETHOSU_PMU_CTRL_ENABLE_Msk; -} - -/** - \brief Disable the PMU -*/ -__STATIC_INLINE void ETHOSU_PMU_Disable(void) -{ - ethosu_pmu_ctrl->PMCR &= ~ETHOSU_PMU_CTRL_ENABLE_Msk; -} - -/** - \brief Set event to count for PMU eventer counter - \param [in] num Event counter (0-ETHOSU_PMU_NCOUNTERS) to configure - \param [in] type Event to count -*/ -__STATIC_INLINE void ETHOSU_PMU_Set_EVTYPER(uint32_t num, enum ethosu_pmu_event_type type) -{ - (*ethosu_pmu_evnt)[num] = pmu_event_value(type); -} - -/** - \brief Get event to count for PMU eventer counter - \param [in] num Event counter (0-ETHOSU_PMU_NCOUNTERS) to configure - \return type Event to count -*/ -__STATIC_INLINE enum ethosu_pmu_event_type ETHOSU_PMU_Get_EVTYPER(uint32_t num) -{ - return pmu_event_type((*ethosu_pmu_evnt)[num]); -} - -/** - \brief Reset cycle counter -*/ -__STATIC_INLINE void ETHOSU_PMU_CYCCNT_Reset(void) -{ - ethosu_pmu_ctrl->PMCR |= ETHOSU_PMU_CTRL_CYCCNT_RESET_Msk; -} - -/** - \brief Reset all event counters -*/ -__STATIC_INLINE void ETHOSU_PMU_EVCNTR_ALL_Reset(void) -{ - ethosu_pmu_ctrl->PMCR |= ETHOSU_PMU_CTRL_EVENTCNT_RESET_Msk; -} - -/** - \brief Enable counters - \param [in] mask Counters to enable - \note Enables one or more of the following: - - event counters (bit 0-ETHOSU_PMU_NCOUNTERS) - - cycle counter (bit 31) -*/ -__STATIC_INLINE void ETHOSU_PMU_CNTR_Enable(uint32_t mask) -{ - ethosu_pmu_ctrl->PMCNTENSET = mask; -} - -/** - \brief Disable counters - \param [in] mask Counters to disable - \note Disables one or more of the following: - - event counters (bit 0-ETHOSU_PMU_NCOUNTERS) - - cycle counter (bit 31) -*/ -__STATIC_INLINE void ETHOSU_PMU_CNTR_Disable(uint32_t mask) -{ - ethosu_pmu_ctrl->PMCNTENCLR = mask; -} - -/** - \brief Determine counters activation - - \return Event count - \param [in] mask Counters to enable - \return a bitmask where bit-set means: - - event counters activated (bit 0-ETHOSU_PMU_NCOUNTERS) - - cycle counter activate (bit 31) - \note ETHOSU specific. Usage breaks CMSIS complience -*/ -__STATIC_INLINE uint32_t ETHOSU_PMU_CNTR_Status() -{ - return ethosu_pmu_ctrl->PMCNTENSET; -} - -/** - \brief Read cycle counter (64 bit) - \return Cycle count - \note Two HW 32-bit registers that can increment independently in-between reads. - To work-around raciness yet still avoid turning - off the event both are read as one value twice. If the latter read - is not greater than the former, it means overflow of LSW without - incrementing MSW has occurred, in which case the former value is used. -*/ -__STATIC_INLINE uint64_t ETHOSU_PMU_Get_CCNTR(void) -{ - uint64_t val1 = ethosu_pmu_ctrl->PMCCNTR; - uint64_t val2 = ethosu_pmu_ctrl->PMCCNTR; - - if (val2 > val1) - { - return val2; - } - return val1; -} - -/** - \brief Set cycle counter (64 bit) - \param [in] val Conter value - \note Two HW 32-bit registers that can increment independently in-between reads. - To work-around raciness, counter is temporary disabled if enabled. - \note ETHOSU specific. Usage breaks CMSIS complience -*/ -__STATIC_INLINE void ETHOSU_PMU_Set_CCNTR(uint64_t val) -{ - uint32_t mask = ETHOSU_PMU_CNTR_Status(); - - if (mask & ETHOSU_PMU_CCNT_Msk) - { - ETHOSU_PMU_CNTR_Disable(ETHOSU_PMU_CCNT_Msk); - } - - ethosu_pmu_ctrl->PMCCNTR = val; - - if (mask & ETHOSU_PMU_CCNT_Msk) - { - ETHOSU_PMU_CNTR_Enable(ETHOSU_PMU_CCNT_Msk); - } -} - -/** - \brief Read event counter - \param [in] num Event counter (0-ETHOSU_PMU_NCOUNTERS) - \return Event count -*/ -__STATIC_INLINE uint32_t ETHOSU_PMU_Get_EVCNTR(uint32_t num) -{ - return (*ethosu_pmu_cntr)[num]; -} - -/** - \brief Set event counter value - \param [in] num Event counter (0-ETHOSU_PMU_NCOUNTERS) - \param [in] val Conter value - \note ETHOSU specific. Usage breaks CMSIS complience -*/ -__STATIC_INLINE void ETHOSU_PMU_Set_EVCNTR(uint32_t num, uint32_t val) -{ - (*ethosu_pmu_cntr)[num] = val; -} -/** - \brief Read counter overflow status - \return Counter overflow status bits for the following: - - event counters (bit 0-ETHOSU_PMU_NCOUNTERS)) - - cycle counter (bit 31) -*/ -__STATIC_INLINE uint32_t ETHOSU_PMU_Get_CNTR_OVS(void) -{ - return ethosu_pmu_ctrl->PMOVSSET; -} - -/** - \brief Clear counter overflow status - \param [in] mask Counter overflow status bits to clear - \note Clears overflow status bits for one or more of the following: - - event counters (bit 0-ETHOSU_PMU_NCOUNTERS) - - cycle counter (bit 31) -*/ -__STATIC_INLINE void ETHOSU_PMU_Set_CNTR_OVS(uint32_t mask) -{ - ethosu_pmu_ctrl->PMOVSCLR = mask; -} - -/** - \brief Enable counter overflow interrupt request - \param [in] mask Counter overflow interrupt request bits to set - \note Sets overflow interrupt request bits for one or more of the following: - - event counters (bit 0-ETHOSU_PMU_NCOUNTERS) - - cycle counter (bit 31) -*/ -__STATIC_INLINE void ETHOSU_PMU_Set_CNTR_IRQ_Enable(uint32_t mask) -{ - ethosu_pmu_ctrl->PMINTSET = mask; -} - -/** - \brief Disable counter overflow interrupt request - \param [in] mask Counter overflow interrupt request bits to clear - \note Clears overflow interrupt request bits for one or more of the following: - - event counters (bit 0-ETHOSU_PMU_NCOUNTERS) - - cycle counter (bit 31) -*/ -__STATIC_INLINE void ETHOSU_PMU_Set_CNTR_IRQ_Disable(uint32_t mask) -{ - ethosu_pmu_ctrl->PMINTCLR = mask; -} - -/** - \brief Get counters overflow interrupt request stiinings - \return mask Counter overflow interrupt request bits - \note Sets overflow interrupt request bits for one or more of the following: - - event counters (bit 0-ETHOSU_PMU_NCOUNTERS) - - cycle counter (bit 31) - \note ETHOSU specific. Usage breaks CMSIS complience -*/ -__STATIC_INLINE uint32_t ETHOSU_PMU_Get_IRQ_Enable() -{ - return ethosu_pmu_ctrl->PMINTSET; -} - -/** - \brief Software increment event counter - \param [in] mask Counters to increment - - event counters (bit 0-ETHOSU_PMU_NCOUNTERS) - - cycle counter (bit 31) - \note Software increment bits for one or more event counters. -*/ -__STATIC_INLINE void ETHOSU_PMU_CNTR_Increment(uint32_t mask) -{ - uint32_t cntrs_active = ETHOSU_PMU_CNTR_Status(); - - if (mask & ETHOSU_PMU_CCNT_Msk) - { - if (mask & ETHOSU_PMU_CCNT_Msk) - { - ETHOSU_PMU_CNTR_Disable(ETHOSU_PMU_CCNT_Msk); - ethosu_pmu_ctrl->PMCCNTR = ETHOSU_PMU_Get_CCNTR() + 1; - if (cntrs_active & ETHOSU_PMU_CCNT_Msk) - { - ETHOSU_PMU_CNTR_Enable(ETHOSU_PMU_CCNT_Msk); - } - } - } - for (int i = 0; i < ETHOSU_PMU_NCOUNTERS; i++) - { - uint32_t cntr = (0x0001 << i); - - if (mask & cntr) - { - ETHOSU_PMU_CNTR_Disable(cntr); - (*ethosu_pmu_cntr)[i]++; - if (cntrs_active & cntr) - { - ETHOSU_PMU_CNTR_Enable(cntr); - } - } - } -} - -#endif /* PMU_ETHOSU_H */ diff --git a/include/pmu_ethosu.h b/include/pmu_ethosu.h new file mode 100644 index 0000000..8fed8bd --- /dev/null +++ b/include/pmu_ethosu.h @@ -0,0 +1,429 @@ +/* + * Copyright (c) 2019-2020 Arm Limited. All rights reserved. + * + * SPDX-License-Identifier: Apache-2.0 + * + * Licensed under the Apache License, Version 2.0 (the License); you may + * not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an AS IS BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef PMU_ETHOSU_H +#define PMU_ETHOSU_H + +#include + +#ifdef __cplusplus +extern "C" { +#endif + +#define ETHOSU_PMU_NCOUNTERS 4 + +typedef volatile struct +{ + uint32_t PMCR; + uint32_t PMCNTENSET; + uint32_t PMCNTENCLR; + uint32_t PMOVSSET; + uint32_t PMOVSCLR; + uint32_t PMINTSET; + uint32_t PMINTCLR; + uint64_t PMCCNTR; + uint32_t PMCCNTR_CFG; +} PMU_Ethosu_ctrl_Type; + +typedef uint32_t PMU_Ethosu_cntr_Type[ETHOSU_PMU_NCOUNTERS]; +typedef uint32_t PMU_Ethosu_evnt_Type[ETHOSU_PMU_NCOUNTERS]; + +/** \brief HW Supported ETHOSU PMU Events + * + * Note: These values are symbolic. Actual HW-values may change. I.e. always use API + * to set/get actual event-type value. + * */ +enum ethosu_pmu_event_type +{ + ETHOSU_PMU_NO_EVENT = 0, + ETHOSU_PMU_CYCLE, + ETHOSU_PMU_NPU_IDLE, + ETHOSU_PMU_MAC_ACTIVE, + ETHOSU_PMU_MAC_ACTIVE_8BIT, + ETHOSU_PMU_MAC_ACTIVE_16BIT, + ETHOSU_PMU_MAC_DPU_ACTIVE, + ETHOSU_PMU_MAC_STALLED_BY_WD_ACC, + ETHOSU_PMU_MAC_STALLED_BY_WD, + ETHOSU_PMU_MAC_STALLED_BY_ACC, + ETHOSU_PMU_MAC_STALLED_BY_IB, + ETHOSU_PMU_MAC_ACTIVE_32BIT, + ETHOSU_PMU_AO_ACTIVE, + ETHOSU_PMU_AO_ACTIVE_8BIT, + ETHOSU_PMU_AO_ACTIVE_16BIT, + ETHOSU_PMU_AO_STALLED_BY_OFMP_OB, + ETHOSU_PMU_AO_STALLED_BY_OFMP, + ETHOSU_PMU_AO_STALLED_BY_OB, + ETHOSU_PMU_AO_STALLED_BY_ACC_IB, + ETHOSU_PMU_AO_STALLED_BY_ACC, + ETHOSU_PMU_AO_STALLED_BY_IB, + ETHOSU_PMU_WD_ACTIVE, + ETHOSU_PMU_WD_STALLED, + ETHOSU_PMU_WD_STALLED_BY_WS, + ETHOSU_PMU_WD_STALLED_BY_WD_BUF, + ETHOSU_PMU_WD_PARSE_ACTIVE, + ETHOSU_PMU_WD_PARSE_STALLED, + ETHOSU_PMU_WD_PARSE_STALLED_IN, + ETHOSU_PMU_WD_PARSE_STALLED_OUT, + ETHOSU_PMU_WD_TRANS_WS, + ETHOSU_PMU_WD_TRANS_WB, + ETHOSU_PMU_WD_TRANS_DW0, + ETHOSU_PMU_WD_TRANS_DW1, + ETHOSU_PMU_AXI0_RD_TRANS_ACCEPTED, + ETHOSU_PMU_AXI0_RD_TRANS_COMPLETED, + ETHOSU_PMU_AXI0_RD_DATA_BEAT_RECEIVED, + ETHOSU_PMU_AXI0_RD_TRAN_REQ_STALLED, + ETHOSU_PMU_AXI0_WR_TRANS_ACCEPTED, + ETHOSU_PMU_AXI0_WR_TRANS_COMPLETED_M, + ETHOSU_PMU_AXI0_WR_TRANS_COMPLETED_S, + ETHOSU_PMU_AXI0_WR_DATA_BEAT_WRITTEN, + ETHOSU_PMU_AXI0_WR_TRAN_REQ_STALLED, + ETHOSU_PMU_AXI0_WR_DATA_BEAT_STALLED, + ETHOSU_PMU_AXI0_ENABLED_CYCLES, + ETHOSU_PMU_AXI0_RD_STALL_LIMIT, + ETHOSU_PMU_AXI0_WR_STALL_LIMIT, + ETHOSU_PMU_AXI1_RD_TRANS_ACCEPTED, + ETHOSU_PMU_AXI1_RD_TRANS_COMPLETED, + ETHOSU_PMU_AXI1_RD_DATA_BEAT_RECEIVED, + ETHOSU_PMU_AXI1_RD_TRAN_REQ_STALLED, + ETHOSU_PMU_AXI1_WR_TRANS_ACCEPTED, + ETHOSU_PMU_AXI1_WR_TRANS_COMPLETED_M, + ETHOSU_PMU_AXI1_WR_TRANS_COMPLETED_S, + ETHOSU_PMU_AXI1_WR_DATA_BEAT_WRITTEN, + ETHOSU_PMU_AXI1_WR_TRAN_REQ_STALLED, + ETHOSU_PMU_AXI1_WR_DATA_BEAT_STALLED, + ETHOSU_PMU_AXI1_ENABLED_CYCLES, + ETHOSU_PMU_AXI1_RD_STALL_LIMIT, + ETHOSU_PMU_AXI1_WR_STALL_LIMIT, + ETHOSU_PMU_AXI_LATENCY_ANY, + ETHOSU_PMU_AXI_LATENCY_32, + ETHOSU_PMU_AXI_LATENCY_64, + ETHOSU_PMU_AXI_LATENCY_128, + ETHOSU_PMU_AXI_LATENCY_256, + ETHOSU_PMU_AXI_LATENCY_512, + ETHOSU_PMU_AXI_LATENCY_1024, + + ETHOSU_PMU_SENTINEL // End-marker (not event) +}; + +extern PMU_Ethosu_ctrl_Type *ethosu_pmu_ctrl; +extern PMU_Ethosu_cntr_Type *ethosu_pmu_cntr; +extern PMU_Ethosu_evnt_Type *ethosu_pmu_evnt; + +#define ETHOSU_PMU_CTRL_ENABLE_Msk (0x0001) +#define ETHOSU_PMU_CTRL_EVENTCNT_RESET_Msk (0x0002) +#define ETHOSU_PMU_CTRL_CYCCNT_RESET_Msk (0x0004) +#define ETHOSU_PMU_CNT1_Msk (1UL << 0) +#define ETHOSU_PMU_CNT2_Msk (1UL << 1) +#define ETHOSU_PMU_CNT3_Msk (1UL << 2) +#define ETHOSU_PMU_CNT4_Msk (1UL << 3) +#define ETHOSU_PMU_CCNT_Msk (1UL << 31) + +/* Transpose functions between HW-event-type and event-id*/ +enum ethosu_pmu_event_type pmu_event_type(uint32_t); +uint32_t pmu_event_value(enum ethosu_pmu_event_type); + +// CMSIS ref API +/** \brief PMU Functions */ + +static inline void ETHOSU_PMU_Enable(void); +static inline void ETHOSU_PMU_Disable(void); + +static inline void ETHOSU_PMU_Set_EVTYPER(uint32_t num, enum ethosu_pmu_event_type type); +static inline enum ethosu_pmu_event_type ETHOSU_PMU_Get_EVTYPER(uint32_t num); + +static inline void ETHOSU_PMU_CYCCNT_Reset(void); +static inline void ETHOSU_PMU_EVCNTR_ALL_Reset(void); + +static inline void ETHOSU_PMU_CNTR_Enable(uint32_t mask); +static inline void ETHOSU_PMU_CNTR_Disable(uint32_t mask); +static inline uint32_t ETHOSU_PMU_CNTR_Status(); + +static inline uint64_t ETHOSU_PMU_Get_CCNTR(void); +static inline void ETHOSU_PMU_Set_CCNTR(uint64_t val); +static inline uint32_t ETHOSU_PMU_Get_EVCNTR(uint32_t num); +static inline void ETHOSU_PMU_Set_EVCNTR(uint32_t num, uint32_t val); + +static inline uint32_t ETHOSU_PMU_Get_CNTR_OVS(void); +static inline void ETHOSU_PMU_Set_CNTR_OVS(uint32_t mask); + +static inline void ETHOSU_PMU_Set_CNTR_IRQ_Enable(uint32_t mask); +static inline void ETHOSU_PMU_Set_CNTR_IRQ_Disable(uint32_t mask); +static inline uint32_t ETHOSU_PMU_Get_IRQ_Enable(); + +static inline void ETHOSU_PMU_CNTR_Increment(uint32_t mask); + +/** + \brief Enable the PMU +*/ +static inline void ETHOSU_PMU_Enable(void) +{ + ethosu_pmu_ctrl->PMCR |= ETHOSU_PMU_CTRL_ENABLE_Msk; +} + +/** + \brief Disable the PMU +*/ +static inline void ETHOSU_PMU_Disable(void) +{ + ethosu_pmu_ctrl->PMCR &= ~ETHOSU_PMU_CTRL_ENABLE_Msk; +} + +/** + \brief Set event to count for PMU eventer counter + \param [in] num Event counter (0-ETHOSU_PMU_NCOUNTERS) to configure + \param [in] type Event to count +*/ +static inline void ETHOSU_PMU_Set_EVTYPER(uint32_t num, enum ethosu_pmu_event_type type) +{ + (*ethosu_pmu_evnt)[num] = pmu_event_value(type); +} + +/** + \brief Get event to count for PMU eventer counter + \param [in] num Event counter (0-ETHOSU_PMU_NCOUNTERS) to configure + \return type Event to count +*/ +static inline enum ethosu_pmu_event_type ETHOSU_PMU_Get_EVTYPER(uint32_t num) +{ + return pmu_event_type((*ethosu_pmu_evnt)[num]); +} + +/** + \brief Reset cycle counter +*/ +static inline void ETHOSU_PMU_CYCCNT_Reset(void) +{ + ethosu_pmu_ctrl->PMCR |= ETHOSU_PMU_CTRL_CYCCNT_RESET_Msk; +} + +/** + \brief Reset all event counters +*/ +static inline void ETHOSU_PMU_EVCNTR_ALL_Reset(void) +{ + ethosu_pmu_ctrl->PMCR |= ETHOSU_PMU_CTRL_EVENTCNT_RESET_Msk; +} + +/** + \brief Enable counters + \param [in] mask Counters to enable + \note Enables one or more of the following: + - event counters (bit 0-ETHOSU_PMU_NCOUNTERS) + - cycle counter (bit 31) +*/ +static inline void ETHOSU_PMU_CNTR_Enable(uint32_t mask) +{ + ethosu_pmu_ctrl->PMCNTENSET = mask; +} + +/** + \brief Disable counters + \param [in] mask Counters to disable + \note Disables one or more of the following: + - event counters (bit 0-ETHOSU_PMU_NCOUNTERS) + - cycle counter (bit 31) +*/ +static inline void ETHOSU_PMU_CNTR_Disable(uint32_t mask) +{ + ethosu_pmu_ctrl->PMCNTENCLR = mask; +} + +/** + \brief Determine counters activation + + \return Event count + \param [in] mask Counters to enable + \return a bitmask where bit-set means: + - event counters activated (bit 0-ETHOSU_PMU_NCOUNTERS) + - cycle counter activate (bit 31) + \note ETHOSU specific. Usage breaks CMSIS complience +*/ +static inline uint32_t ETHOSU_PMU_CNTR_Status() +{ + return ethosu_pmu_ctrl->PMCNTENSET; +} + +/** + \brief Read cycle counter (64 bit) + \return Cycle count + \note Two HW 32-bit registers that can increment independently in-between reads. + To work-around raciness yet still avoid turning + off the event both are read as one value twice. If the latter read + is not greater than the former, it means overflow of LSW without + incrementing MSW has occurred, in which case the former value is used. +*/ +static inline uint64_t ETHOSU_PMU_Get_CCNTR(void) +{ + uint64_t val1 = ethosu_pmu_ctrl->PMCCNTR; + uint64_t val2 = ethosu_pmu_ctrl->PMCCNTR; + + if (val2 > val1) + { + return val2; + } + return val1; +} + +/** + \brief Set cycle counter (64 bit) + \param [in] val Conter value + \note Two HW 32-bit registers that can increment independently in-between reads. + To work-around raciness, counter is temporary disabled if enabled. + \note ETHOSU specific. Usage breaks CMSIS complience +*/ +static inline void ETHOSU_PMU_Set_CCNTR(uint64_t val) +{ + uint32_t mask = ETHOSU_PMU_CNTR_Status(); + + if (mask & ETHOSU_PMU_CCNT_Msk) + { + ETHOSU_PMU_CNTR_Disable(ETHOSU_PMU_CCNT_Msk); + } + + ethosu_pmu_ctrl->PMCCNTR = val; + + if (mask & ETHOSU_PMU_CCNT_Msk) + { + ETHOSU_PMU_CNTR_Enable(ETHOSU_PMU_CCNT_Msk); + } +} + +/** + \brief Read event counter + \param [in] num Event counter (0-ETHOSU_PMU_NCOUNTERS) + \return Event count +*/ +static inline uint32_t ETHOSU_PMU_Get_EVCNTR(uint32_t num) +{ + return (*ethosu_pmu_cntr)[num]; +} + +/** + \brief Set event counter value + \param [in] num Event counter (0-ETHOSU_PMU_NCOUNTERS) + \param [in] val Conter value + \note ETHOSU specific. Usage breaks CMSIS complience +*/ +static inline void ETHOSU_PMU_Set_EVCNTR(uint32_t num, uint32_t val) +{ + (*ethosu_pmu_cntr)[num] = val; +} +/** + \brief Read counter overflow status + \return Counter overflow status bits for the following: + - event counters (bit 0-ETHOSU_PMU_NCOUNTERS)) + - cycle counter (bit 31) +*/ +static inline uint32_t ETHOSU_PMU_Get_CNTR_OVS(void) +{ + return ethosu_pmu_ctrl->PMOVSSET; +} + +/** + \brief Clear counter overflow status + \param [in] mask Counter overflow status bits to clear + \note Clears overflow status bits for one or more of the following: + - event counters (bit 0-ETHOSU_PMU_NCOUNTERS) + - cycle counter (bit 31) +*/ +static inline void ETHOSU_PMU_Set_CNTR_OVS(uint32_t mask) +{ + ethosu_pmu_ctrl->PMOVSCLR = mask; +} + +/** + \brief Enable counter overflow interrupt request + \param [in] mask Counter overflow interrupt request bits to set + \note Sets overflow interrupt request bits for one or more of the following: + - event counters (bit 0-ETHOSU_PMU_NCOUNTERS) + - cycle counter (bit 31) +*/ +static inline void ETHOSU_PMU_Set_CNTR_IRQ_Enable(uint32_t mask) +{ + ethosu_pmu_ctrl->PMINTSET = mask; +} + +/** + \brief Disable counter overflow interrupt request + \param [in] mask Counter overflow interrupt request bits to clear + \note Clears overflow interrupt request bits for one or more of the following: + - event counters (bit 0-ETHOSU_PMU_NCOUNTERS) + - cycle counter (bit 31) +*/ +static inline void ETHOSU_PMU_Set_CNTR_IRQ_Disable(uint32_t mask) +{ + ethosu_pmu_ctrl->PMINTCLR = mask; +} + +/** + \brief Get counters overflow interrupt request stiinings + \return mask Counter overflow interrupt request bits + \note Sets overflow interrupt request bits for one or more of the following: + - event counters (bit 0-ETHOSU_PMU_NCOUNTERS) + - cycle counter (bit 31) + \note ETHOSU specific. Usage breaks CMSIS complience +*/ +static inline uint32_t ETHOSU_PMU_Get_IRQ_Enable() +{ + return ethosu_pmu_ctrl->PMINTSET; +} + +/** + \brief Software increment event counter + \param [in] mask Counters to increment + - event counters (bit 0-ETHOSU_PMU_NCOUNTERS) + - cycle counter (bit 31) + \note Software increment bits for one or more event counters. +*/ +static inline void ETHOSU_PMU_CNTR_Increment(uint32_t mask) +{ + uint32_t cntrs_active = ETHOSU_PMU_CNTR_Status(); + + if (mask & ETHOSU_PMU_CCNT_Msk) + { + if (mask & ETHOSU_PMU_CCNT_Msk) + { + ETHOSU_PMU_CNTR_Disable(ETHOSU_PMU_CCNT_Msk); + ethosu_pmu_ctrl->PMCCNTR = ETHOSU_PMU_Get_CCNTR() + 1; + if (cntrs_active & ETHOSU_PMU_CCNT_Msk) + { + ETHOSU_PMU_CNTR_Enable(ETHOSU_PMU_CCNT_Msk); + } + } + } + for (int i = 0; i < ETHOSU_PMU_NCOUNTERS; i++) + { + uint32_t cntr = (0x0001 << i); + + if (mask & cntr) + { + ETHOSU_PMU_CNTR_Disable(cntr); + (*ethosu_pmu_cntr)[i]++; + if (cntrs_active & cntr) + { + ETHOSU_PMU_CNTR_Enable(cntr); + } + } + } +} + +#ifdef __cplusplus +} +#endif + +#endif /* PMU_ETHOSU_H */ diff --git a/src/ethosu_pmu.c b/src/ethosu_pmu.c new file mode 100644 index 0000000..5e5490c --- /dev/null +++ b/src/ethosu_pmu.c @@ -0,0 +1,102 @@ +/* + * Copyright (c) 2019-2020 Arm Limited. All rights reserved. + * + * SPDX-License-Identifier: Apache-2.0 + * + * Licensed under the Apache License, Version 2.0 (the License); you may + * not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an AS IS BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/***************************************************************************** + * Includes + *****************************************************************************/ + +#include "ethosu55_interface.h" +#include "ethosu_common.h" +#include +#include +#include +#include + +/***************************************************************************** + * Defines + *****************************************************************************/ + +#define COMMA , +#define SEMICOLON ; + +#define ETHOSU_PMU_CTRL_BASE (NPU_BASE + ((uint32_t)0x180)) +#define ETHOSU_PMU_CNTR_BASE (NPU_BASE + ((uint32_t)0x300)) +#define ETHOSU_PMU_EVNT_BASE (NPU_BASE + ((uint32_t)0x380)) + +#define EVTYPE(A, name) \ + case PMU_EVENT_TYPE_##name: \ + return ETHOSU_PMU_##name + +#define EVID(A, name) (PMU_EVENT_TYPE_##name) + +/***************************************************************************** + * Variables + *****************************************************************************/ + +PMU_Ethosu_ctrl_Type *ethosu_pmu_ctrl = (PMU_Ethosu_ctrl_Type *)ETHOSU_PMU_CTRL_BASE; +PMU_Ethosu_cntr_Type *ethosu_pmu_cntr = (PMU_Ethosu_cntr_Type *)ETHOSU_PMU_CNTR_BASE; +PMU_Ethosu_evnt_Type *ethosu_pmu_evnt = (PMU_Ethosu_evnt_Type *)ETHOSU_PMU_EVNT_BASE; + +static const enum pmu_event_type eventbyid[] = {EXPAND_PMU_EVENT_TYPE(EVID, COMMA)}; + +/***************************************************************************** + * Functions + *****************************************************************************/ + +enum ethosu_pmu_event_type pmu_event_type(uint32_t id) +{ + switch (id) + { + EXPAND_PMU_EVENT_TYPE(EVTYPE, SEMICOLON); + } + + return ETHOSU_PMU_SENTINEL; +} + +uint32_t pmu_event_value(enum ethosu_pmu_event_type event) +{ + if (!(event < ETHOSU_PMU_SENTINEL) || (event < 0)) + { + return (uint32_t)(-1); + } + + return eventbyid[event]; +} + +void ethosu_pmu_driver_init(void) +{ +#ifdef PMU_AUTOINIT + *ethosu_pmu_ctrl = (PMU_Ethosu_ctrl_Type){.PMCR = INIT_PMCR, + .PMCNTENSET = INIT_PMCNTENSET, + .PMCNTENCLR = INIT_PMCNTENCLR, + .PMOVSSET = INIT_PMOVSSET, + .PMOVSCLR = INIT_PMOVSCLR, + .PMINTSET = INIT_PMINTSET, + .PMINTCLR = INIT_PMINTCLR, + .PMCCNTR = INIT_PMCCNTR, + .PMCCNTR_CFG = INIT_PMCCNTR_CFG}; + + for (int i = 0; i < ETHOSU_PMU_NCOUNTERS; i++) + { + *ethosu_pmu_cntr[i] = 0; + *ethosu_pmu_evnt[i] = 0; + } +#endif +} + +void ethosu_pmu_driver_exit(void) {} -- cgit v1.2.1