diff options
author | Jim Quigley <jim.quigley@arm.com> | 2020-02-17 15:47:51 +0000 |
---|---|---|
committer | Chris Kay <chris@cjkay.com> | 2020-02-24 19:56:00 +0000 |
commit | 3970a6f995d1909b29b83ff9542a7433ce8d6946 (patch) | |
tree | 1206b509bb6c2735212b8b46da3cf6f822e21769 | |
parent | 358c8140980c6c09237cf657d29eb4b641bf4b34 (diff) |
sgm776: Add sgm776 platform
This patch adds support for the sgm776 platform.
Change-Id: I62db113e37b1e688957a982c13f13c58cf995a4c
Signed-off-by: Jim Quigley <jim.quigley@arm.com>
75 files changed, 6601 insertions, 0 deletions
diff --git a/module/dmc500/include/mod_dmc500.h b/module/dmc500/include/mod_dmc500.h new file mode 100644 index 00000000..d611af83 --- /dev/null +++ b/module/dmc500/include/mod_dmc500.h @@ -0,0 +1,568 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + * + * Description: + * DMC-500 module. + */ + +#ifndef MOD_DMC500_H +#define MOD_DMC500_H + +#include <stdint.h> +#include <fwk_macros.h> +#include <fwk_module.h> +#include <mod_log.h> +#include <mod_timer.h> + +/*! + * \addtogroup GroupModules Modules + * @{ + */ + +/*! + * \addtogroup GroupDMC DMC-500 Driver + * + * \details Please consult the Arm CoreLink DMC-500 Dynamic Memory Controller + * Technical Reference Manual for details on the specific registers that + * are programmed here. + * @{ + */ + +/*! + * \brief DMC-500 register definitions + */ +struct mod_dmc500_reg { + /*! + * \cond + * @{ + */ + FWK_R uint32_t SI0_SI_STATUS; + FWK_R uint32_t SI0_SI_INTERRUPT_STATUS; + FWK_R uint32_t SI0_TZ_FAIL_ADDRESS_LOW; + FWK_R uint32_t SI0_TZ_FAIL_ADDRESS_HIGH; + FWK_R uint32_t SI0_TZ_FAIL_CONTROL; + FWK_R uint32_t SI0_TZ_FAIL_ID; + FWK_R uint32_t SI0_PMU_REQ_INT_INFO; + FWK_RW uint32_t SI0_PMU_REQ_COUNT0; + FWK_RW uint32_t SI0_PMU_REQ_COUNT1; + FWK_RW uint32_t SI0_PMU_REQ_COUNT2; + FWK_RW uint32_t SI0_PMU_REQ_COUNT3; + FWK_RW uint32_t SI0_PMU_SCLK_COUNT_COUNT; + FWK_RW uint32_t SI0_SI_STATE_CONTROL; + FWK_W uint32_t SI0_SI_FLUSH_CONTROL; + FWK_RW uint32_t ADDRESS_CONTROL; + FWK_RW uint32_t DECODE_CONTROL; + FWK_RW uint32_t ADDRESS_MAP; + FWK_RW uint32_t RANK_REMAP_CONTROL; + FWK_RW uint32_t SI0_SI_INTERRUPT_CONTROL; + FWK_W uint32_t SI0_SI_INTERRUPT_CLR; + FWK_RW uint32_t TZ_ACTION; + FWK_R uint32_t SI0_TZ_REGION_BASE_LOW_0; + FWK_R uint32_t SI0_TZ_REGION_BASE_HIGH_0; + FWK_RW uint32_t SI0_TZ_REGION_TOP_LOW_0; + FWK_RW uint32_t SI0_TZ_REGION_TOP_HIGH_0; + FWK_RW uint32_t SI0_TZ_REGION_ATTRIBUTES_0; + FWK_RW uint32_t SI0_TZ_REGION_ID_ACCESS_0; + FWK_RW uint32_t SI0_TZ_REGION_BASE_LOW_1; + FWK_RW uint32_t SI0_TZ_REGION_BASE_HIGH_1; + FWK_RW uint32_t SI0_TZ_REGION_TOP_LOW_1; + FWK_RW uint32_t SI0_TZ_REGION_TOP_HIGH_1; + FWK_RW uint32_t SI0_TZ_REGION_ATTRIBUTES_1; + FWK_RW uint32_t SI0_TZ_REGION_ID_ACCESS_1; + FWK_RW uint32_t SI0_TZ_REGION_BASE_LOW_2; + FWK_RW uint32_t SI0_TZ_REGION_BASE_HIGH_2; + FWK_RW uint32_t SI0_TZ_REGION_TOP_LOW_2; + FWK_RW uint32_t SI0_TZ_REGION_TOP_HIGH_2; + FWK_RW uint32_t SI0_TZ_REGION_ATTRIBUTES_2; + FWK_RW uint32_t SI0_TZ_REGION_ID_ACCESS_2; + FWK_RW uint32_t SI0_TZ_REGION_BASE_LOW_3; + FWK_RW uint32_t SI0_TZ_REGION_BASE_HIGH_3; + FWK_RW uint32_t SI0_TZ_REGION_TOP_LOW_3; + FWK_RW uint32_t SI0_TZ_REGION_TOP_HIGH_3; + FWK_RW uint32_t SI0_TZ_REGION_ATTRIBUTES_3; + FWK_RW uint32_t SI0_TZ_REGION_ID_ACCESS_3; + FWK_RW uint32_t SI0_TZ_REGION_BASE_LOW_4; + FWK_RW uint32_t SI0_TZ_REGION_BASE_HIGH_4; + FWK_RW uint32_t SI0_TZ_REGION_TOP_LOW_4; + FWK_RW uint32_t SI0_TZ_REGION_TOP_HIGH_4; + FWK_RW uint32_t SI0_TZ_REGION_ATTRIBUTES_4; + FWK_RW uint32_t SI0_TZ_REGION_ID_ACCESS_4; + FWK_RW uint32_t SI0_TZ_REGION_BASE_LOW_5; + FWK_RW uint32_t SI0_TZ_REGION_BASE_HIGH_5; + FWK_RW uint32_t SI0_TZ_REGION_TOP_LOW_5; + FWK_RW uint32_t SI0_TZ_REGION_TOP_HIGH_5; + FWK_RW uint32_t SI0_TZ_REGION_ATTRIBUTES_5; + FWK_RW uint32_t SI0_TZ_REGION_ID_ACCESS_5; + FWK_RW uint32_t SI0_TZ_REGION_BASE_LOW_6; + FWK_RW uint32_t SI0_TZ_REGION_BASE_HIGH_6; + FWK_RW uint32_t SI0_TZ_REGION_TOP_LOW_6; + FWK_RW uint32_t SI0_TZ_REGION_TOP_HIGH_6; + FWK_RW uint32_t SI0_TZ_REGION_ATTRIBUTES_6; + FWK_RW uint32_t SI0_TZ_REGION_ID_ACCESS_6; + FWK_RW uint32_t SI0_TZ_REGION_BASE_LOW_7; + FWK_RW uint32_t SI0_TZ_REGION_BASE_HIGH_7; + FWK_RW uint32_t SI0_TZ_REGION_TOP_LOW_7; + FWK_RW uint32_t SI0_TZ_REGION_TOP_HIGH_7; + FWK_RW uint32_t SI0_TZ_REGION_ATTRIBUTES_7; + FWK_RW uint32_t SI0_TZ_REGION_ID_ACCESS_7; + FWK_RW uint32_t SI0_TZ_REGION_BASE_LOW_8; + FWK_RW uint32_t SI0_TZ_REGION_BASE_HIGH_8; + FWK_RW uint32_t SI0_TZ_REGION_TOP_LOW_8; + FWK_RW uint32_t SI0_TZ_REGION_TOP_HIGH_8; + FWK_RW uint32_t SI0_TZ_REGION_ATTRIBUTES_8; + FWK_RW uint32_t SI0_TZ_REGION_ID_ACCESS_8; + FWK_RW uint32_t SI0_PMU_REQ_CONTROL; + FWK_RW uint32_t SI0_PMU_REQ_ATTRIBUTE_MASK_0; + FWK_RW uint32_t SI0_PMU_REQ_ATTRIBUTE_MATCH_0; + FWK_RW uint32_t SI0_PMU_REQ_ATTRIBUTE_MASK_1; + FWK_RW uint32_t SI0_PMU_REQ_ATTRIBUTE_MATCH_1; + FWK_RW uint32_t SI0_PMU_REQ_ATTRIBUTE_MASK_2; + FWK_RW uint32_t SI0_PMU_REQ_ATTRIBUTE_MATCH_2; + FWK_RW uint32_t SI0_PMU_REQ_ATTRIBUTE_MASK_3; + FWK_RW uint32_t SI0_PMU_REQ_ATTRIBUTE_MATCH_3; + FWK_RW uint32_t SI0_THRESHOLD_CONTROL; + uint8_t RESERVED0[0x200 - 0x154]; + FWK_R uint32_t SI1_SI_STATUS; + FWK_R uint32_t SI1_SI_INTERRUPT_STATUS; + FWK_R uint32_t SI1_TZ_FAIL_ADDRESS_LOW; + FWK_R uint32_t SI1_TZ_FAIL_ADDRESS_HIGH; + FWK_R uint32_t SI1_TZ_FAIL_CONTROL; + FWK_R uint32_t SI1_TZ_FAIL_ID; + FWK_R uint32_t SI1_PMU_REQ_INT_INFO; + FWK_RW uint32_t SI1_PMU_REQ_COUNT0; + FWK_RW uint32_t SI1_PMU_REQ_COUNT1; + FWK_RW uint32_t SI1_PMU_REQ_COUNT2; + FWK_RW uint32_t SI1_PMU_REQ_COUNT3; + FWK_RW uint32_t SI1_PMU_SCLK_COUNT_COUNT; + FWK_RW uint32_t SI1_SI_STATE_CONTROL; + FWK_W uint32_t SI1_SI_FLUSH_CONTROL; + uint8_t RESERVED1[0x248 - 0x238]; + FWK_RW uint32_t SI1_SI_INTERRUPT_CONTROL; + FWK_W uint32_t SI1_SI_INTERRUPT_CLR; + uint32_t RESERVED2; + FWK_R uint32_t SI1_TZ_REGION_BASE_LOW_0; + FWK_R uint32_t SI1_TZ_REGION_BASE_HIGH_0; + FWK_RW uint32_t SI1_TZ_REGION_TOP_LOW_0; + FWK_RW uint32_t SI1_TZ_REGION_TOP_HIGH_0; + FWK_RW uint32_t SI1_TZ_REGION_ATTRIBUTES_0; + FWK_RW uint32_t SI1_TZ_REGION_ID_ACCESS_0; + FWK_RW uint32_t SI1_TZ_REGION_BASE_LOW_1; + FWK_RW uint32_t SI1_TZ_REGION_BASE_HIGH_1; + FWK_RW uint32_t SI1_TZ_REGION_TOP_LOW_1; + FWK_RW uint32_t SI1_TZ_REGION_TOP_HIGH_1; + FWK_RW uint32_t SI1_TZ_REGION_ATTRIBUTES_1; + FWK_RW uint32_t SI1_TZ_REGION_ID_ACCESS_1; + FWK_RW uint32_t SI1_TZ_REGION_BASE_LOW_2; + FWK_RW uint32_t SI1_TZ_REGION_BASE_HIGH_2; + FWK_RW uint32_t SI1_TZ_REGION_TOP_LOW_2; + FWK_RW uint32_t SI1_TZ_REGION_TOP_HIGH_2; + FWK_RW uint32_t SI1_TZ_REGION_ATTRIBUTES_2; + FWK_RW uint32_t SI1_TZ_REGION_ID_ACCESS_2; + FWK_RW uint32_t SI1_TZ_REGION_BASE_LOW_3; + FWK_RW uint32_t SI1_TZ_REGION_BASE_HIGH_3; + FWK_RW uint32_t SI1_TZ_REGION_TOP_LOW_3; + FWK_RW uint32_t SI1_TZ_REGION_TOP_HIGH_3; + FWK_RW uint32_t SI1_TZ_REGION_ATTRIBUTES_3; + FWK_RW uint32_t SI1_TZ_REGION_ID_ACCESS_3; + FWK_RW uint32_t SI1_TZ_REGION_BASE_LOW_4; + FWK_RW uint32_t SI1_TZ_REGION_BASE_HIGH_4; + FWK_RW uint32_t SI1_TZ_REGION_TOP_LOW_4; + FWK_RW uint32_t SI1_TZ_REGION_TOP_HIGH_4; + FWK_RW uint32_t SI1_TZ_REGION_ATTRIBUTES_4; + FWK_RW uint32_t SI1_TZ_REGION_ID_ACCESS_4; + FWK_RW uint32_t SI1_TZ_REGION_BASE_LOW_5; + FWK_RW uint32_t SI1_TZ_REGION_BASE_HIGH_5; + FWK_RW uint32_t SI1_TZ_REGION_TOP_LOW_5; + FWK_RW uint32_t SI1_TZ_REGION_TOP_HIGH_5; + FWK_RW uint32_t SI1_TZ_REGION_ATTRIBUTES_5; + FWK_RW uint32_t SI1_TZ_REGION_ID_ACCESS_5; + FWK_RW uint32_t SI1_TZ_REGION_BASE_LOW_6; + FWK_RW uint32_t SI1_TZ_REGION_BASE_HIGH_6; + FWK_RW uint32_t SI1_TZ_REGION_TOP_LOW_6; + FWK_RW uint32_t SI1_TZ_REGION_TOP_HIGH_6; + FWK_RW uint32_t SI1_TZ_REGION_ATTRIBUTES_6; + FWK_RW uint32_t SI1_TZ_REGION_ID_ACCESS_6; + FWK_RW uint32_t SI1_TZ_REGION_BASE_LOW_7; + FWK_RW uint32_t SI1_TZ_REGION_BASE_HIGH_7; + FWK_RW uint32_t SI1_TZ_REGION_TOP_LOW_7; + FWK_RW uint32_t SI1_TZ_REGION_TOP_HIGH_7; + FWK_RW uint32_t SI1_TZ_REGION_ATTRIBUTES_7; + FWK_RW uint32_t SI1_TZ_REGION_ID_ACCESS_7; + FWK_RW uint32_t SI1_TZ_REGION_BASE_LOW_8; + FWK_RW uint32_t SI1_TZ_REGION_BASE_HIGH_8; + FWK_RW uint32_t SI1_TZ_REGION_TOP_LOW_8; + FWK_RW uint32_t SI1_TZ_REGION_TOP_HIGH_8; + FWK_RW uint32_t SI1_TZ_REGION_ATTRIBUTES_8; + FWK_RW uint32_t SI1_TZ_REGION_ID_ACCESS_8; + FWK_RW uint32_t SI1_PMU_REQ_CONTROL; + FWK_RW uint32_t SI1_PMU_REQ_ATTRIBUTE_MASK_0; + FWK_RW uint32_t SI1_PMU_REQ_ATTRIBUTE_MATCH_0; + FWK_RW uint32_t SI1_PMU_REQ_ATTRIBUTE_MASK_1; + FWK_RW uint32_t SI1_PMU_REQ_ATTRIBUTE_MATCH_1; + FWK_RW uint32_t SI1_PMU_REQ_ATTRIBUTE_MASK_2; + FWK_RW uint32_t SI1_PMU_REQ_ATTRIBUTE_MATCH_2; + FWK_RW uint32_t SI1_PMU_REQ_ATTRIBUTE_MASK_3; + FWK_RW uint32_t SI1_PMU_REQ_ATTRIBUTE_MATCH_3; + FWK_RW uint32_t SI1_THRESHOLD_CONTROL; + uint8_t RESERVED3[0x400 - 0x354]; + FWK_R uint32_t DCB_STATUS; + FWK_R uint32_t M_INTERRUPT_STATUS; + FWK_R uint32_t PMU_DCB_INT_INFO; + FWK_W uint32_t DCB_STATE_CONTROL; + uint32_t RESERVED4; + FWK_RW uint32_t QUEUE_THRESHOLD_CONTROL_31_00; + FWK_RW uint32_t QUEUE_THRESHOLD_CONTROL_63_32; + uint8_t RESERVED5[0x42C - 0x41C]; + FWK_RW uint32_t DCB_INTERRUPT_CONTROL; + FWK_W uint32_t DCB_INTERRUPT_CLR; + FWK_RW uint32_t PMU_DCB_CONTROL; + FWK_RW uint32_t PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MASK_0; + FWK_RW uint32_t PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MATCH_0; + FWK_RW uint32_t PMU_DATA_CONTROL_BLOCK_COUNT_0; + FWK_RW uint32_t PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MASK_1; + FWK_RW uint32_t PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MATCH_1; + FWK_RW uint32_t PMU_DATA_CONTROL_BLOCK_COUNT_1; + FWK_RW uint32_t PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MASK_2; + FWK_RW uint32_t PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MATCH_2; + FWK_RW uint32_t PMU_DATA_CONTROL_BLOCK_COUNT_2; + FWK_RW uint32_t PMU_TAG_ENTRIES_ATTRIBUTE_MASK; + FWK_RW uint32_t PMU_TAG_ENTRIES_ATTRIBUTE_MATCH; + FWK_RW uint32_t PMU_TAG_ENTRIES_COUNT; + FWK_RW uint32_t PMU_MCLK_COUNT_COUNT; + uint32_t RESERVED6; + FWK_R uint32_t ERR_RAMECC_FR; + uint32_t RESERVED7; + FWK_RW uint32_t ERR_RAMECC_CTLR; + uint32_t RESERVED8; + FWK_RW uint32_t ERR_RAMECC_STATUS; + uint32_t RESERVED9; + FWK_RW uint32_t ERR_RAMECC_ADDR; + FWK_RW uint32_t ERR_RAMECC_ADDR2; + FWK_RW uint32_t ERR_RAMECC_MISC0; + uint32_t RESERVED10[3]; + FWK_W uint32_t ERR_RAMECC_INJECT; + uint8_t RESERVED11[0x500 - 0x4A4]; + FWK_R uint32_t QUEUE_STATUS; + uint32_t RESERVED12; + FWK_R uint32_t PMU_QE_INT_INFO; + FWK_RW uint32_t QUEUE_STATE_CONTROL; + FWK_RW uint32_t QE_INTERRUPT_CONTROL; + FWK_W uint32_t QE_INTERRUPT_CLR; + FWK_RW uint32_t RANK_TURNAROUND_CONTROL; + FWK_RW uint32_t HIT_TURNAROUND_CONTROL; + FWK_RW uint32_t QOS_CLASS_CONTROL; + FWK_RW uint32_t ESCALATION_CONTROL; + FWK_RW uint32_t QV_CONTROL_31_00; + FWK_RW uint32_t QV_CONTROL_63_32; + FWK_RW uint32_t RT_CONTROL_31_00; + FWK_RW uint32_t RT_CONTROL_63_32; + FWK_RW uint32_t TIMEOUT_CONTROL; + FWK_RW uint32_t WRITE_PRIORITY_CONTROL_31_00; + FWK_RW uint32_t WRITE_PRIORITY_CONTROL_63_32; + uint32_t RESERVED13; + FWK_RW uint32_t DIR_TURNAROUND_CONTROL; + FWK_RW uint32_t HIT_PREDICTION_CONTROL; + FWK_RW uint32_t REFRESH_ENABLE; + FWK_R uint32_t REFRESH_STATUS; + FWK_R uint32_t REFRESH_STATUS_FG; + FWK_RW uint32_t REFRESH_PRIORITY; + FWK_RW uint32_t MC_UPDATE_CONTROL; + FWK_RW uint32_t PHY_UPDATE_CONTROL; + FWK_RW uint32_t PHY_MASTER_CONTROL; + FWK_RW uint32_t LOW_POWER_CONTROL; + FWK_RW uint32_t PMU_QE_CONTROL; + FWK_RW uint32_t PMU_QE_MUX; + FWK_RW uint32_t PMU_QOS_ENGINE_ATTRIBUTE_MASK_0; + FWK_RW uint32_t PMU_QOS_ENGINE_ATTRIBUTE_MATCH_0; + FWK_RW uint32_t PMU_QOS_ENGINE_COUNT_0; + FWK_RW uint32_t PMU_QOS_ENGINE_ATTRIBUTE_MASK_1; + FWK_RW uint32_t PMU_QOS_ENGINE_ATTRIBUTE_MATCH_1; + FWK_RW uint32_t PMU_QOS_ENGINE_COUNT_1; + FWK_RW uint32_t PMU_QOS_ENGINE_ATTRIBUTE_MASK_2; + FWK_RW uint32_t PMU_QOS_ENGINE_ATTRIBUTE_MATCH_2; + FWK_RW uint32_t PMU_QOS_ENGINE_COUNT_2; + FWK_RW uint32_t PMU_QUEUED_ENTRIES_ATTRIBUTE_MASK; + FWK_RW uint32_t PMU_QUEUED_ENTRIES_ATTRIBUTE_MATCH; + FWK_RW uint32_t PMU_QUEUED_ENTRIES_COUNT; + uint8_t RESERVED14[0x600 - 0x5A8]; + FWK_R uint32_t MI_STATUS; + FWK_R uint32_t RANKS_READY; + FWK_R uint32_t RANKS_RESET; + FWK_R uint32_t RANKS_DEEP_POWER_DOWN; + FWK_R uint32_t RANKS_SELF_REFRESH; + FWK_R uint32_t RANKS_POWERED_DOWN; + FWK_R uint32_t RANKS_CLOCK_DISABLED; + FWK_R uint32_t PHY_STATUS0; + FWK_R uint32_t PHY_STATUS1; + uint32_t RESERVED15; + FWK_R uint32_t PMU_MI_INT_INFO; + uint32_t RESERVED16; + FWK_RW uint32_t MI_STATE_CONTROL; + FWK_RW uint32_t PHY_CONFIG; + FWK_RW uint32_t DIRECT_CMD_SETTINGS; + FWK_RW uint32_t DIRECT_CMD; + FWK_RW uint32_t DIRECT_CLK_DISABLE; + FWK_RW uint32_t DIRECT_ODT; + FWK_RW uint32_t DCI_STRB; + FWK_RW uint32_t DCI_DATA; + FWK_W uint32_t DCI_DATA_CLR; + FWK_W uint32_t RANK_STATUS_OVERRIDE; + FWK_W uint32_t CLK_STATUS_OVERRIDE; + FWK_W uint32_t BANK_STATUS_OVERRIDE; + FWK_RW uint32_t MI_INTERRUPT_CONTROL; + FWK_W uint32_t MI_INTERRUPT_CLR; + FWK_RW uint32_t MEMORY_TYPE; + FWK_RW uint32_t FORMAT_CONTROL; + FWK_RW uint32_t FEATURE_CONTROL; + FWK_RW uint32_t POWER_DOWN_CONTROL; + FWK_RW uint32_t REFRESH_CONTROL; + FWK_RW uint32_t ODT_WR_CONTROL_31_00; + uint32_t RESERVED17; + FWK_RW uint32_t ODT_RD_CONTROL_31_00; + uint32_t RESERVED18; + FWK_RW uint32_t PHY_WRDATA_CS_CONTROL_31_00; + uint32_t RESERVED19; + FWK_RW uint32_t PHY_RDDATA_CS_CONTROL_31_00; + uint32_t RESERVED20; + FWK_RW uint32_t PHYUPD_INIT; + FWK_RW uint32_t PHY_POWER_CONTROL; + uint32_t RESERVED21; + FWK_RW uint32_t ODT_TIMING; + FWK_RW uint32_t T_REFI; + FWK_RW uint32_t T_RFC; + FWK_RW uint32_t T_RCD; + FWK_RW uint32_t T_RAS; + FWK_RW uint32_t T_RP; + FWK_RW uint32_t T_RRD; + FWK_RW uint32_t T_ACT_WINDOW; + FWK_RW uint32_t T_RTR; + FWK_RW uint32_t T_RTW; + FWK_RW uint32_t T_RTP; + FWK_RW uint32_t T_RDPDEN; + FWK_RW uint32_t T_WR; + FWK_RW uint32_t T_WTR; + FWK_RW uint32_t T_WTW; + FWK_RW uint32_t T_XTMW; + FWK_RW uint32_t T_WRPDEN; + FWK_RW uint32_t T_CLOCK_CONTROL; + FWK_RW uint32_t T_EP; + FWK_RW uint32_t T_XP; + FWK_RW uint32_t T_ESR; + FWK_RW uint32_t T_XSR; + uint32_t RESERVED22; + FWK_RW uint32_t T_COMPLETION_CHECKS; + FWK_RW uint32_t T_RDDATA_EN; + FWK_RW uint32_t T_PHYRDLAT; + FWK_RW uint32_t T_PHYWRLAT; + FWK_RW uint32_t T_PHY_TRAIN; + FWK_R uint32_t ERR_PHY_FR; + uint32_t RESERVED23; + FWK_RW uint32_t ERR_PHY_CTLR; + uint32_t RESERVED24; + FWK_RW uint32_t ERR_PHY_STATUS; + uint32_t RESERVED25; + FWK_RW uint32_t ERR_PHY_ADDR; + FWK_RW uint32_t ERR_PHY_ADDR2; + FWK_RW uint32_t ERR_PHY_MISC0; + uint8_t RESERVED26[0x74C - 0x73C]; + FWK_W uint32_t ERR_PHY_INJECT; + FWK_RW uint32_t PMU_MI_CONTROL; + FWK_RW uint32_t PMU_MEMORY_IF_ATTRIBUTE_MASK_0; + FWK_RW uint32_t PMU_MEMORY_IF_ATTRIBUTE_MATCH_0; + FWK_RW uint32_t PMU_MEMORY_IF_COUNT_0; + FWK_RW uint32_t PMU_MEMORY_IF_ATTRIBUTE_MASK_1; + FWK_RW uint32_t PMU_MEMORY_IF_ATTRIBUTE_MATCH_1; + FWK_RW uint32_t PMU_MEMORY_IF_COUNT_1; + FWK_RW uint32_t PMU_BANK_STATES_ATTRIBUTE_MASK; + FWK_RW uint32_t PMU_BANK_STATES_ATTRIBUTE_MATCH; + FWK_RW uint32_t PMU_BANK_STATES_COUNT; + FWK_RW uint32_t PMU_RANK_STATES_ATTRIBUTE_MASK; + FWK_RW uint32_t PMU_RANK_STATES_ATTRIBUTE_MATCH; + FWK_RW uint32_t PMU_RANK_STATES_COUNT; + uint8_t RESERVED27[0xF00 - 0x784]; + FWK_R uint32_t MEMC_CONFIG; + uint32_t RESERVED28[3]; + FWK_R uint32_t CFG_INTERRUPT_STATUS; + FWK_R uint32_t CFG_FAILED_ACCESS_INT_INFO; + uint8_t RESERVED29[0xF30 - 0xF18]; + FWK_RW uint32_t CFG_INTERRUPT_CONTROL; + uint32_t RESERVED30; + FWK_W uint32_t CFG_INTERRUPT_CLR; + uint8_t RESERVED31[0xFC0 - 0xF3C]; + FWK_RW uint32_t INTEGRATION_TEST_CONTROL; + FWK_RW uint32_t INTEGRATION_TEST_OUTPUT; + uint32_t RESERVED32[2]; + FWK_R uint32_t PERIPH_ID_4; + uint32_t RESERVED33[3]; + FWK_R uint32_t PERIPH_ID_0; + FWK_R uint32_t PERIPH_ID_1; + FWK_R uint32_t PERIPH_ID_2; + FWK_R uint32_t PERIPH_ID_3; + FWK_R uint32_t COMPONENT_ID_0; + FWK_R uint32_t COMPONENT_ID_1; + FWK_R uint32_t COMPONENT_ID_2; + FWK_R uint32_t COMPONENT_ID_3; + /*! + * \endcond + * @} + */ +}; + +/*! + * \brief SI_STATE_CONTROL mask used to prevent request stalling. + */ +#define MOD_DMC500_SI_STATE_CONTROL_GO 0 + +/*! + * \brief SI_STATE_CONTROL mask used to enable request stalling. + */ +#define MOD_DMC500_SI_STATE_CONTROL_STALL_REQ (1 << 0) + +/*! + * \brief SI_STATUS mask used to confirm that request stalling is active. + */ +#define MOD_DMC500_SI_STATUS_STALL_ACK (1 << 0) + +/*! + * \brief SI_STATUS mask used to read the empty bit. + */ +#define MOD_DMC500_SI_STATUS_EMPTY (1 << 1) + +/*! + * \brief QUEUE_STATE_CONTROL mask used to prevent request stalling. + */ +#define MOD_DMC500_QUEUE_STATE_CONTROL_GO 0 + +/*! + * \brief QUEUE_STATE_CONTROL mask used to enable request stalling. + */ +#define MOD_DMC500_QUEUE_STATE_CONTROL_STALL_REQ (1 << 0) + +/*! + * \brief QUEUE_STATUS mask used to confirm that request stalling is active. + */ +#define MOD_DMC500_QUEUE_STATUS_STALL_ACK (1 << 0) + +/*! + * \brief QUEUE_STATUS mask used to read the empty bit. + */ +#define MOD_DMC500_QUEUE_STATUS_EMPTY (1 << 1) + +/*! + * \brief MI_STATUS mask used to read the idle bit. + */ +#define MOD_DMC500_MI_STATUS_IDLE (1 << 0) + +/*! + * \brief MI_STATUS mask used to read the empty bit. + */ +#define MOD_DMC500_MI_STATUS_EMPTY (1 << 1) + +/*! + * \brief Create the ADDRESS_MAP value. + * + * \param SHUTTER The address shutter. + * + * \return The ADDRESS_MAP value. + */ +#define ADDRESS_MAP_VAL(SHUTTER) ((1 << 8) | (SHUTTER)) + +/*! + * \brief Create the ADDRESS_CONTROL value. + * + * \param RANK Number of bits for the rank. + * \param BANK Number of bits for the bank. + * \param ROW Number of bits for the row. + * \param COL Number of bits for the column. + * + * \return The ADDRESS_CONTROL value. + */ +#define ADDRESS_CONTROL_VAL(RANK, BANK, ROW, COL) (((RANK) << 24) | \ + ((BANK) << 16) | \ + ((ROW) << 8) | \ + (COL)) + +/*! + * \brief Create the MEMORY_TYPE value + * + * \param BANK_GROUP Bank group. + * \param WIDTH Memory device width. + * \param TYPE Memory type. + * + * \return The MEMORY_TYPE value. + */ +#define MEMORY_TYPE_VAL(BANK_GROUP, WIDTH, TYPE) (((BANK_GROUP) << 16) | \ + ((WIDTH) << 8) | \ + (TYPE)) + +/*! + * \brief Create the FORMAT_CONTROL value. + * + * \param BURST Memory burst. + * + * \return The FORMAT_CONTROL value. + */ +#define FORMAT_CONTROL_VAL(BURST) ((BURST) << 8) + +/*! + * \brief Element configuration. + */ +struct mod_dmc500_element_config { + /*! Base address of the DMC-500 device's registers */ + uintptr_t dmc; + /*! Element identifier of the associated DDR PHY-500 device */ + fwk_id_t ddr_phy_id; +}; + +/*! + * \brief API of the DDR PHY associate to the DMC + */ +struct mod_dmc_ddr_phy_api { + /*! + * \brief Configure a DDR PHY500 device + * + * \param element_id Element identifier corresponding to the device to + * configure. + * + * \retval FWK_SUCCESS if the operation succeed. + * \return one of the error code otherwise. + */ + int (*configure)(fwk_id_t element_id); +}; + +/*! + * \brief DMC-500 module configuration. + */ +struct mod_dmc500_module_config { + /*! + * Element identifier of the timer used for delays when programming the + * DMC-500 + */ + fwk_id_t timer_id; + /*! DDR PHY module ID */ + fwk_id_t ddr_phy_module_id; + /*! DDR PHY API ID */ + fwk_id_t ddr_phy_api_id; + /*! Initial value for the dmc registers */ + const struct mod_dmc500_reg *reg_val; + /*! Pointer to a product-specific function that issues direct commands */ + void (*direct_ddr_cmd)(struct mod_dmc500_reg *dmc); +}; + +/*! + * \brief DMC-500 module description. + */ +extern const struct fwk_module module_dmc500; + +/*! + * @} + */ + +/*! + * @} + */ + +#endif /* MOD_DMC500_H */ diff --git a/module/dmc500/src/Makefile b/module/dmc500/src/Makefile new file mode 100644 index 00000000..ae4f2159 --- /dev/null +++ b/module/dmc500/src/Makefile @@ -0,0 +1,11 @@ +# +# Arm SCP/MCP Software +# Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. +# +# SPDX-License-Identifier: BSD-3-Clause +# + +BS_LIB_NAME := mod_dmc500 +BS_LIB_SOURCES += mod_dmc500.c + +include $(BS_DIR)/lib.mk diff --git a/module/dmc500/src/mod_dmc500.c b/module/dmc500/src/mod_dmc500.c new file mode 100644 index 00000000..5e5e3d73 --- /dev/null +++ b/module/dmc500/src/mod_dmc500.c @@ -0,0 +1,390 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + * + * Description: + * DMC-500 driver + */ + +#include <assert.h> +#include <fwk_mm.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <fwk_status.h> +#include <mod_dmc500.h> + +static struct mod_log_api *log_api; +static struct mod_dmc_ddr_phy_api *ddr_phy_api; +static struct mod_timer_api *timer_api; + +static int dmc500_config(struct mod_dmc500_reg *dmc, fwk_id_t ddr_phy_id); + +/* Framework API */ +static int mod_dmc500_init(fwk_id_t module_id, unsigned int element_count, + const void *data) +{ + return FWK_SUCCESS; +} + +static int mod_dmc500_element_init(fwk_id_t element_id, unsigned int unused, + const void *data) +{ + assert(data != NULL); + + return FWK_SUCCESS; +} + +static int mod_dmc500_bind(fwk_id_t id, unsigned int round) +{ + int status; + const struct mod_dmc500_module_config *module_config; + + /* Nothing to do in the second round of calls. */ + if (round == 1) + return FWK_SUCCESS; + + /* Nothing to do in case of elements. */ + if (fwk_module_is_valid_element_id(id)) + return FWK_SUCCESS; + + module_config = fwk_module_get_data(fwk_module_id_dmc500); + assert(module_config != NULL); + + status = fwk_module_bind(FWK_ID_MODULE(FWK_MODULE_IDX_LOG), + MOD_LOG_API_ID, &log_api); + if (status != FWK_SUCCESS) + return status; + + status = fwk_module_bind(module_config->ddr_phy_module_id, + module_config->ddr_phy_api_id, &ddr_phy_api); + if (status != FWK_SUCCESS) + return status; + + status = fwk_module_bind(module_config->timer_id, + FWK_ID_API(FWK_MODULE_IDX_TIMER, 0), &timer_api); + if (status != FWK_SUCCESS) + return status; + + return FWK_SUCCESS; +} + +static int mod_dmc500_start(fwk_id_t id) +{ + const struct mod_dmc500_element_config *element_config; + struct mod_dmc500_reg *dmc; + + /* Nothing to start for the module */ + if (fwk_module_is_valid_module_id(id)) + return FWK_SUCCESS; + + element_config = fwk_module_get_data(id); + dmc = (struct mod_dmc500_reg *)element_config->dmc; + + return dmc500_config(dmc, element_config->ddr_phy_id); +} + +const struct fwk_module module_dmc500 = { + .name = "DMC500", + .type = FWK_MODULE_TYPE_DRIVER, + .init = mod_dmc500_init, + .element_init = mod_dmc500_element_init, + .bind = mod_dmc500_bind, + .start = mod_dmc500_start, + .api_count = 0, + .event_count = 0, +}; + + +static int dmc500_config(struct mod_dmc500_reg *dmc, fwk_id_t ddr_phy_id) +{ + int status; + uint64_t timeout; + uint64_t remaining_ticks; + uint64_t counter; + const struct mod_dmc500_reg *reg_val; + const struct mod_dmc500_module_config *module_config; + + module_config = fwk_module_get_data(fwk_module_id_dmc500); + reg_val = module_config->reg_val; + + status = log_api->log(MOD_LOG_GROUP_DEBUG, + "[DDR] Initialising DMC500 at 0x%x\n", (uintptr_t)dmc); + if (status != FWK_SUCCESS) + return status; + + dmc->ADDRESS_CONTROL = reg_val->ADDRESS_CONTROL; + dmc->RANK_REMAP_CONTROL = reg_val->RANK_REMAP_CONTROL; + dmc->MEMORY_TYPE = reg_val->MEMORY_TYPE; + dmc->FORMAT_CONTROL = reg_val->FORMAT_CONTROL; + dmc->DECODE_CONTROL = reg_val->DECODE_CONTROL; + dmc->FEATURE_CONTROL = reg_val->FEATURE_CONTROL; + dmc->ODT_WR_CONTROL_31_00 = reg_val->ODT_WR_CONTROL_31_00; + dmc->ODT_RD_CONTROL_31_00 = reg_val->ODT_RD_CONTROL_31_00; + dmc->ODT_TIMING = reg_val->ODT_TIMING; + + status = log_api->log(MOD_LOG_GROUP_DEBUG, + "[DDR] Setting timing settings\n"); + if (status != FWK_SUCCESS) + return status; + + dmc->T_REFI = reg_val->T_REFI; + dmc->T_RFC = reg_val->T_RFC; + dmc->T_RDPDEN = reg_val->T_RDPDEN; + dmc->T_RCD = reg_val->T_RCD; + dmc->T_RAS = reg_val->T_RAS; + dmc->T_RP = reg_val->T_RP; + dmc->T_RRD = reg_val->T_RRD; + dmc->T_ACT_WINDOW = reg_val->T_ACT_WINDOW; + dmc->T_RTR = reg_val->T_RTR; + dmc->T_RTW = reg_val->T_RTW; + dmc->T_RTP = reg_val->T_RTP; + dmc->T_WR = reg_val->T_WR; + dmc->T_WTR = reg_val->T_WTR; + dmc->T_WTW = reg_val->T_WTW; + dmc->T_XTMW = reg_val->T_XTMW; + dmc->T_CLOCK_CONTROL = reg_val->T_CLOCK_CONTROL; + dmc->T_EP = reg_val->T_EP; + dmc->T_XP = reg_val->T_XP; + dmc->T_ESR = reg_val->T_ESR; + dmc->T_XSR = reg_val->T_XSR; + + status = log_api->log(MOD_LOG_GROUP_DEBUG, + "[DDR] Setting address map\n"); + if (status != FWK_SUCCESS) + return status; + + dmc->ADDRESS_MAP = reg_val->ADDRESS_MAP; + + status = log_api->log(MOD_LOG_GROUP_DEBUG, + "[DDR] Setting PMU settings\n"); + if (status != FWK_SUCCESS) + return status; + + dmc->SI0_SI_INTERRUPT_CONTROL = reg_val->SI0_SI_INTERRUPT_CONTROL; + dmc->SI0_PMU_REQ_CONTROL = reg_val->SI0_PMU_REQ_CONTROL; + dmc->SI0_PMU_REQ_ATTRIBUTE_MASK_0 = reg_val->SI0_PMU_REQ_ATTRIBUTE_MASK_0; + dmc->SI0_PMU_REQ_ATTRIBUTE_MATCH_0 = reg_val->SI0_PMU_REQ_ATTRIBUTE_MATCH_0; + dmc->SI0_PMU_REQ_ATTRIBUTE_MASK_1 = reg_val->SI0_PMU_REQ_ATTRIBUTE_MASK_1; + dmc->SI0_PMU_REQ_ATTRIBUTE_MATCH_1 = reg_val->SI0_PMU_REQ_ATTRIBUTE_MATCH_1; + dmc->SI0_PMU_REQ_ATTRIBUTE_MASK_2 = reg_val->SI0_PMU_REQ_ATTRIBUTE_MASK_2; + dmc->SI0_PMU_REQ_ATTRIBUTE_MATCH_2 = reg_val->SI0_PMU_REQ_ATTRIBUTE_MATCH_2; + dmc->SI0_PMU_REQ_ATTRIBUTE_MASK_3 = reg_val->SI0_PMU_REQ_ATTRIBUTE_MASK_3; + dmc->SI0_PMU_REQ_ATTRIBUTE_MATCH_3 = reg_val->SI0_PMU_REQ_ATTRIBUTE_MATCH_3; + dmc->SI0_THRESHOLD_CONTROL = reg_val->SI0_THRESHOLD_CONTROL; + dmc->SI1_SI_INTERRUPT_CONTROL = reg_val->SI1_SI_INTERRUPT_CONTROL; + dmc->SI1_PMU_REQ_CONTROL = reg_val->SI1_PMU_REQ_CONTROL; + dmc->SI1_PMU_REQ_ATTRIBUTE_MASK_0 = reg_val->SI1_PMU_REQ_ATTRIBUTE_MASK_0; + dmc->SI1_PMU_REQ_ATTRIBUTE_MATCH_0 = reg_val->SI1_PMU_REQ_ATTRIBUTE_MATCH_0; + dmc->SI1_PMU_REQ_ATTRIBUTE_MASK_1 = reg_val->SI1_PMU_REQ_ATTRIBUTE_MASK_1; + dmc->SI1_PMU_REQ_ATTRIBUTE_MATCH_1 = reg_val->SI1_PMU_REQ_ATTRIBUTE_MATCH_1; + dmc->SI1_PMU_REQ_ATTRIBUTE_MASK_2 = reg_val->SI1_PMU_REQ_ATTRIBUTE_MASK_2; + dmc->SI1_PMU_REQ_ATTRIBUTE_MATCH_2 = reg_val->SI1_PMU_REQ_ATTRIBUTE_MATCH_2; + dmc->SI1_PMU_REQ_ATTRIBUTE_MASK_3 = reg_val->SI1_PMU_REQ_ATTRIBUTE_MASK_3; + dmc->SI1_PMU_REQ_ATTRIBUTE_MATCH_3 = reg_val->SI1_PMU_REQ_ATTRIBUTE_MATCH_3; + dmc->SI1_THRESHOLD_CONTROL = reg_val->SI1_THRESHOLD_CONTROL; + dmc->QUEUE_THRESHOLD_CONTROL_31_00 = reg_val->QUEUE_THRESHOLD_CONTROL_31_00; + dmc->QUEUE_THRESHOLD_CONTROL_63_32 = reg_val->QUEUE_THRESHOLD_CONTROL_63_32; + dmc->DCB_INTERRUPT_CONTROL = reg_val->DCB_INTERRUPT_CONTROL; + dmc->PMU_DCB_CONTROL = reg_val->PMU_DCB_CONTROL; + dmc->PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MASK_0 = + reg_val->PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MASK_0; + dmc->PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MATCH_0 = + reg_val->PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MATCH_0; + dmc->PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MASK_1 = + reg_val->PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MASK_1; + dmc->PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MATCH_1 = + reg_val->PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MATCH_1; + dmc->PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MASK_2 = + reg_val->PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MASK_2; + dmc->PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MATCH_2 = + reg_val->PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MATCH_2; + dmc->PMU_TAG_ENTRIES_ATTRIBUTE_MASK = + reg_val->PMU_TAG_ENTRIES_ATTRIBUTE_MASK; + dmc->PMU_TAG_ENTRIES_ATTRIBUTE_MATCH = + reg_val->PMU_TAG_ENTRIES_ATTRIBUTE_MATCH; + dmc->QE_INTERRUPT_CONTROL = reg_val->QE_INTERRUPT_CONTROL; + dmc->RANK_TURNAROUND_CONTROL = reg_val->RANK_TURNAROUND_CONTROL; + dmc->HIT_TURNAROUND_CONTROL = reg_val->HIT_TURNAROUND_CONTROL; + dmc->QOS_CLASS_CONTROL = reg_val->QOS_CLASS_CONTROL; + dmc->ESCALATION_CONTROL = reg_val->ESCALATION_CONTROL; + dmc->QV_CONTROL_31_00 = reg_val->QV_CONTROL_31_00; + dmc->QV_CONTROL_63_32 = reg_val->QV_CONTROL_63_32; + dmc->RT_CONTROL_31_00 = reg_val->RT_CONTROL_31_00; + dmc->RT_CONTROL_63_32 = reg_val->RT_CONTROL_63_32; + dmc->TIMEOUT_CONTROL = reg_val->TIMEOUT_CONTROL; + dmc->WRITE_PRIORITY_CONTROL_31_00 = reg_val->WRITE_PRIORITY_CONTROL_31_00; + dmc->WRITE_PRIORITY_CONTROL_63_32 = reg_val->WRITE_PRIORITY_CONTROL_63_32; + dmc->DIR_TURNAROUND_CONTROL = reg_val->DIR_TURNAROUND_CONTROL; + dmc->HIT_PREDICTION_CONTROL = reg_val->HIT_PREDICTION_CONTROL; + dmc->REFRESH_PRIORITY = reg_val->REFRESH_PRIORITY; + dmc->MC_UPDATE_CONTROL = reg_val->MC_UPDATE_CONTROL; + dmc->PHY_UPDATE_CONTROL = reg_val->PHY_UPDATE_CONTROL; + dmc->PHY_MASTER_CONTROL = reg_val->PHY_MASTER_CONTROL; + dmc->LOW_POWER_CONTROL = reg_val->LOW_POWER_CONTROL; + dmc->PMU_QE_CONTROL = reg_val->PMU_QE_CONTROL; + dmc->PMU_QE_MUX = reg_val->PMU_QE_MUX; + dmc->PMU_QOS_ENGINE_ATTRIBUTE_MASK_0 = + reg_val->PMU_QOS_ENGINE_ATTRIBUTE_MASK_0; + dmc->PMU_QOS_ENGINE_ATTRIBUTE_MATCH_0 = + reg_val->PMU_QOS_ENGINE_ATTRIBUTE_MATCH_0; + dmc->PMU_QOS_ENGINE_ATTRIBUTE_MASK_1 = + reg_val->PMU_QOS_ENGINE_ATTRIBUTE_MASK_1; + dmc->PMU_QOS_ENGINE_ATTRIBUTE_MATCH_1 = + reg_val->PMU_QOS_ENGINE_ATTRIBUTE_MATCH_1; + dmc->PMU_QOS_ENGINE_ATTRIBUTE_MASK_2 = + reg_val->PMU_QOS_ENGINE_ATTRIBUTE_MASK_2; + dmc->PMU_QOS_ENGINE_ATTRIBUTE_MATCH_2 = + reg_val->PMU_QOS_ENGINE_ATTRIBUTE_MATCH_2; + dmc->PMU_QUEUED_ENTRIES_ATTRIBUTE_MASK = + reg_val->PMU_QUEUED_ENTRIES_ATTRIBUTE_MASK; + dmc->PMU_QUEUED_ENTRIES_ATTRIBUTE_MATCH = + reg_val->PMU_QUEUED_ENTRIES_ATTRIBUTE_MATCH; + dmc->MI_INTERRUPT_CONTROL = reg_val->MI_INTERRUPT_CONTROL; + dmc->POWER_DOWN_CONTROL = reg_val->POWER_DOWN_CONTROL; + dmc->REFRESH_CONTROL = reg_val->REFRESH_CONTROL; + dmc->PMU_MI_CONTROL = reg_val->PMU_MI_CONTROL; + dmc->PMU_MEMORY_IF_ATTRIBUTE_MASK_0 = + reg_val->PMU_MEMORY_IF_ATTRIBUTE_MASK_0; + dmc->PMU_MEMORY_IF_ATTRIBUTE_MATCH_0 = + reg_val->PMU_MEMORY_IF_ATTRIBUTE_MATCH_0; + dmc->PMU_MEMORY_IF_ATTRIBUTE_MASK_1 = + reg_val->PMU_MEMORY_IF_ATTRIBUTE_MASK_1; + dmc->PMU_MEMORY_IF_ATTRIBUTE_MATCH_1 = + reg_val->PMU_MEMORY_IF_ATTRIBUTE_MATCH_1; + dmc->PMU_BANK_STATES_ATTRIBUTE_MASK = + reg_val->PMU_BANK_STATES_ATTRIBUTE_MASK; + dmc->PMU_BANK_STATES_ATTRIBUTE_MATCH = + reg_val->PMU_BANK_STATES_ATTRIBUTE_MATCH; + dmc->PMU_RANK_STATES_ATTRIBUTE_MASK = + reg_val->PMU_RANK_STATES_ATTRIBUTE_MASK; + dmc->PMU_RANK_STATES_ATTRIBUTE_MATCH = + reg_val->PMU_RANK_STATES_ATTRIBUTE_MATCH; + dmc->CFG_INTERRUPT_CONTROL = reg_val->CFG_INTERRUPT_CONTROL; + dmc->T_RDDATA_EN = reg_val->T_RDDATA_EN; + dmc->T_PHYRDLAT = reg_val->T_PHYRDLAT; + dmc->T_PHYWRLAT = reg_val->T_PHYWRLAT; + + dmc->ERR_RAMECC_CTLR = reg_val->ERR_RAMECC_CTLR; + + status = log_api->log(MOD_LOG_GROUP_DEBUG, + "[DDR] Setting PHY-related settings\n"); + if (status != FWK_SUCCESS) + return status; + + dmc->PHY_POWER_CONTROL = reg_val->PHY_POWER_CONTROL; + dmc->T_PHY_TRAIN = reg_val->T_PHY_TRAIN; + dmc->PHYUPD_INIT = reg_val->PHYUPD_INIT; + + dmc->PHY_CONFIG = 0x03000000; + dmc->PHY_CONFIG = 0x0600000A; + dmc->PHY_CONFIG = 0x01000001; + + status = ddr_phy_api->configure(ddr_phy_id); + if (status != FWK_SUCCESS) + return status; + + dmc->PHY_CONFIG = 0x01000001; + dmc->PHY_CONFIG = 0x01000000; + dmc->PHY_CONFIG = 0x00000003; + + status = log_api->log(MOD_LOG_GROUP_DEBUG, + "[DDR] Doing direct DDR commands\n"); + if (status != FWK_SUCCESS) + return status; + + module_config->direct_ddr_cmd(dmc); + + dmc->REFRESH_ENABLE = reg_val->REFRESH_ENABLE; + + status = log_api->log(MOD_LOG_GROUP_DEBUG, + "[DDR] Setting dmc in READY mode\n"); + if (status != FWK_SUCCESS) + return status; + + status = timer_api->time_to_timestamp(module_config->timer_id, + 1000 * 1000, &timeout); + if (status != FWK_SUCCESS) + return status; + + status = timer_api->get_counter(module_config->timer_id, &counter); + if (status != FWK_SUCCESS) + return status; + + timeout += counter; + + while ((dmc->MI_STATUS & MOD_DMC500_MI_STATUS_IDLE) != + MOD_DMC500_MI_STATUS_IDLE) { + status = timer_api->remaining(module_config->timer_id, timeout, + &remaining_ticks); + if (status != FWK_SUCCESS) + return status; + + if (remaining_ticks == 0) + goto timeout; + } + + dmc->MI_STATE_CONTROL = reg_val->MI_STATE_CONTROL; + dmc->QUEUE_STATE_CONTROL = reg_val->QUEUE_STATE_CONTROL; + dmc->SI0_SI_STATE_CONTROL = reg_val->SI0_SI_STATE_CONTROL; + dmc->SI1_SI_STATE_CONTROL = reg_val->SI1_SI_STATE_CONTROL; + + status = log_api->log(MOD_LOG_GROUP_DEBUG, + "[DDR] Waiting for Queue stall = 0...\n"); + if (status != FWK_SUCCESS) + return status; + + while ((dmc->QUEUE_STATUS & MOD_DMC500_QUEUE_STATUS_STALL_ACK) != 0) { + status = timer_api->remaining(module_config->timer_id, timeout, + &remaining_ticks); + if (status != FWK_SUCCESS) + return status; + + if (remaining_ticks == 0) + goto timeout; + } + + status = log_api->log(MOD_LOG_GROUP_DEBUG, + "[DDR] Waiting for SI0 stall = 0...\n"); + if (status != FWK_SUCCESS) + return FWK_SUCCESS; + + while ((dmc->SI0_SI_STATUS & MOD_DMC500_SI_STATUS_STALL_ACK) != 0) { + status = timer_api->remaining(module_config->timer_id, timeout, + &remaining_ticks); + if (status != FWK_SUCCESS) + return status; + + if (remaining_ticks == 0) + goto timeout; + } + + status = log_api->log(MOD_LOG_GROUP_DEBUG, + "[DDR] Waiting for SI1 stall = 0...\n"); + if (status != FWK_SUCCESS) + return status; + + while ((dmc->SI1_SI_STATUS & MOD_DMC500_SI_STATUS_STALL_ACK) != 0) { + status = timer_api->remaining(module_config->timer_id, timeout, + &remaining_ticks); + if (status != FWK_SUCCESS) + return status; + + if (remaining_ticks == 0) + goto timeout; + } + + status = log_api->log(MOD_LOG_GROUP_DEBUG, "[DDR] DMC init done.\n"); + if (status != FWK_SUCCESS) + return status; + + return FWK_SUCCESS; + +timeout: + status = log_api->log(MOD_LOG_GROUP_ERROR, + "[DDR] Timed out in DMC500 init.\n"); + if (status != FWK_SUCCESS) + return status; + return FWK_E_TIMEOUT; +} diff --git a/product/sgm776/include/fmw_cmsis.h b/product/sgm776/include/fmw_cmsis.h new file mode 100644 index 00000000..ece8426c --- /dev/null +++ b/product/sgm776/include/fmw_cmsis.h @@ -0,0 +1,30 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2018-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef FMW_CMSIS_H +#define FMW_CMSIS_H + +#define __CHECK_DEVICE_DEFINES +#define __CM3_REV 0x0201 +#define __MPU_PRESENT 1 +#define __NVIC_PRIO_BITS 3 +#define __Vendor_SysTickConfig 0 + +typedef enum IRQn { + NonMaskableInt_IRQn = -14, + MemoryManagement_IRQn = -12, + BusFault_IRQn = -11, + UsageFault_IRQn = -10, + SVCall_IRQn = -5, + DebugMonitor_IRQn = -4, + PendSV_IRQn = -2, + SysTick_IRQn = -1, +} IRQn_Type; + +#include <core_cm3.h> + +#endif /* FMW_CMSIS_H */ diff --git a/product/sgm776/include/sgm776_core.h b/product/sgm776/include/sgm776_core.h new file mode 100644 index 00000000..ef0ccac0 --- /dev/null +++ b/product/sgm776/include/sgm776_core.h @@ -0,0 +1,15 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef SGM776_CORE_H +#define SGM776_CORE_H + +#define SGM776_CORE_PER_CLUSTER_MAX 8 + +unsigned int sgm776_core_get_count(void); + +#endif /* SGM776_CORE_H */ diff --git a/product/sgm776/include/sgm776_irq.h b/product/sgm776/include/sgm776_irq.h new file mode 100644 index 00000000..b664a005 --- /dev/null +++ b/product/sgm776/include/sgm776_irq.h @@ -0,0 +1,210 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef SGM776_IRQ_H +#define SGM776_IRQ_H + +#include <fwk_interrupt.h> + +#define WDOG_IRQ FWK_INTERRUPT_NMI /* SCP Watchdog (SP805) */ + +enum sgm776_irq { + TIM32KHZ_IRQ = 0, /* 32KHz Physical Timer */ + CDBG_PWR_UP_REQ_IRQ = 1, /* Coresight Debug Power Request */ + CSYS_PWR_UP_REQ_IRQ = 2, /* Coresight System Power Request */ + CDBG_RST_REQ_IRQ = 3, /* Coresight Debug Reset Request */ + RESERVED4_IRQ = 4, /* Reserved */ + RESERVED5_IRQ = 5, /* Reserved */ + RESERVED6_IRQ = 6, /* Reserved */ + RESERVED7_IRQ = 7, /* Reserved */ + RESERVED8_IRQ = 8, /* Reserved */ + RESERVED9_IRQ = 9, /* Reserved */ + RESERVED10_IRQ = 10, /* Reserved */ + RESERVED11_IRQ = 11, /* Reserved */ + RESERVED12_IRQ = 12, /* Reserved */ + RESERVED13_IRQ = 13, /* Reserved */ + RESERVED14_IRQ = 14, /* Reserved */ + RESERVED15_IRQ = 15, /* Reserved */ + SOC_WAKEUP0_IRQ = 16, /* SoC Expansion Wakeup */ + SOC_WAKEUP1_IRQ = 17, /* SoC Expansion Wakeup */ + SOC_WAKEUP2_IRQ = 18, /* SoC Expansion Wakeup */ + SOC_WAKEUP3_IRQ = 19, /* SoC Expansion Wakeup */ + SOC_WAKEUP4_IRQ = 20, /* SoC Expansion Wakeup */ + SOC_WAKEUP5_IRQ = 21, /* SoC Expansion Wakeup */ + SOC_WAKEUP6_IRQ = 22, /* SoC Expansion Wakeup */ + SOC_WAKEUP7_IRQ = 23, /* SoC Expansion Wakeup */ + SOC_WAKEUP8_IRQ = 24, /* SoC Expansion Wakeup */ + SOC_WAKEUP9_IRQ = 25, /* SoC Expansion Wakeup */ + SOC_WAKEUP10_IRQ = 26, /* SoC Expansion Wakeup */ + SOC_WAKEUP11_IRQ = 27, /* SoC Expansion Wakeup */ + SOC_WAKEUP12_IRQ = 28, /* SoC Expansion Wakeup */ + SOC_WAKEUP13_IRQ = 29, /* SoC Expansion Wakeup */ + SOC_WAKEUP14_IRQ = 30, /* SoC Expansion Wakeup */ + SOC_WAKEUP15_IRQ = 31, /* SoC Expansion Wakeup */ + PPU_SCP_IRQ = 32, /* SCP Power Policy Unit */ + TIMREFCLK_IRQ = 33, /* REFCLK Physical Timer */ + MHU_HIGH_PRIO_IRQ = 34, /* MHU High Priority */ + MHU_LOW_PRIO_IRQ = 35, /* MHU Low Priority */ + MHU_SECURE_IRQ = 36, /* MHU Secure */ + CTI_TRIGGER0_IRQ = 37, /* SCP CTI Trigger */ + CTI_TRIGGER1_IRQ = 38, /* SCP CTI Trigger */ + GIC_ERROR_ECC_IRQ = 39, /* GIC Error (ECC Fatal) */ + GIC_ERROR_AXIM_IRQ = 40, /* GIC Error (AXIM) */ + DMC_RESERVED0_IRQ = 41, /* DMC, Reserved */ + DMC_0_ERROR_ECC_IRQ = 42, /* DMC0 Combined ECC Error */ + DMC_0_ERROR_ACCESS_IRQ = 43, /* DMC0 Combined Misc Access Error */ + DMC_RESERVED1_IRQ = 44, /* DMC, Reserved */ + DMC_RESERVED2_IRQ = 45, /* DMC, Reserved */ + DMC_1_ERROR_ECC_IRQ = 46, /* DMC1 Combined ECC Error */ + DMC_1_ERROR_ACCESS_IRQ = 47, /* DMC1 Combined Misc Access Error */ + DMC_RESERVED3_IRQ = 48, /* DMC, Reserved */ + DMC_RESERVED4_IRQ = 49, /* DMC, Reserved */ + DMC_2_ERROR_ECC_IRQ = 50, /* DMC2 Combined ECC Error */ + DMC_2_ERROR_ACCESS_IRQ = 51, /* DMC2 Combined Misc Access Error */ + DMC_RESERVED5_IRQ = 52, /* DMC, Reserved */ + DMC_RESERVED6_IRQ = 53, /* DMC, Reserved */ + DMC_3_ERROR_ECC_IRQ = 54, /* DMC3 Combined ECC Error */ + DMC_3_ERROR_ACCESS_IRQ = 55, /* DMC3 Combined Misc Access Error */ + DMC_RESERVED7_IRQ = 56, /* DMC, Reserved */ + RESERVED57_IRQ = 57, /* Reserved */ + RESERVED58_IRQ = 58, /* Reserved */ + RESERVED59_IRQ = 59, /* Reserved */ + RESERVED60_IRQ = 60, /* Reserved */ + RESERVED61_IRQ = 61, /* Reserved */ + RESERVED62_IRQ = 62, /* Reserved */ + RESERVED63_IRQ = 63, /* Reserved */ + PPU_CLUS0CORE0_IRQ = 64, /* Cluster 0 Core 0 Power Policy Unit */ + PPU_CLUS0CORE1_IRQ = 65, /* Cluster 0 Core 1 Power Policy Unit */ + PPU_CLUS0CORE2_IRQ = 66, /* Cluster 0 Core 2 Power Policy Unit */ + PPU_CLUS0CORE3_IRQ = 67, /* Cluster 0 Core 3 Power Policy Unit */ + PPU_CLUS0_IRQ = 68, /* Cluster 0 Power Policy Unit */ + PPU_CLUS1CORE0_IRQ = 69, /* Cluster 1 Core 0 Power Policy Unit */ + PPU_CLUS1CORE1_IRQ = 70, /* Cluster 1 Core 1 Power Policy Unit */ + PPU_CLUS1CORE2_IRQ = 71, /* Cluster 1 Core 2 Power Policy Unit */ + PPU_CLUS1CORE3_IRQ = 72, /* Cluster 1 Core 3 Power Policy Unit */ + PPU_CLUS1_IRQ = 73, /* Cluster 1 Power Policy Unit */ + PPU_SYS0_IRQ = 74, /* System Power Policy Unit 0 */ + PPU_SYS1_IRQ = 75, /* System Power Policy Unit 1 */ + PPU_GPU_IRQ = 76, /* GPU Power Policy Unit */ + PPU_VPU_IRQ = 77, /* Video Power Policy Unit */ + PPU_DPU_IRQ = 78, /* Display Power Policy Unit 0 */ + RESERVED79_IRQ = 79, /* Reserved */ + RESERVED80_IRQ = 80, /* Reserved */ + PPU_DEBUG_IRQ = 81, /* DBGSYS Power Policy Unit */ + PPU_DEBUG_CHAIN_IRQ = 82, /* Debug chain Power Policy Unit */ + RESERVED83_IRQ = 83, /* Reserved */ + RESERVED84_IRQ = 84, /* Reserved */ + RESERVED85_IRQ = 85, /* Reserved */ + RESERVED86_IRQ = 86, /* Reserved */ + RESERVED87_IRQ = 87, /* Reserved */ + RESERVED88_IRQ = 88, /* Reserved */ + RESERVED89_IRQ = 89, /* Reserved */ + PPU_CLUS0CORE4_IRQ = 90, /* Cluster 0 Core 4 Power Policy Unit */ + PPU_CLUS0CORE5_IRQ = 91, /* Cluster 0 Core 5 Power Policy Unit */ + PPU_CLUS0CORE6_IRQ = 92, /* Cluster 0 Core 6 Power Policy Unit */ + PPU_CLUS0CORE7_IRQ = 93, /* Cluster 0 Core 7 Power Policy Unit */ + PPU_CLUS1CORE4_IRQ = 94, /* Cluster 1 Core 4 Power Policy Unit */ + PPU_CLUS1CORE5_IRQ = 95, /* Cluster 1 Core 5 Power Policy Unit */ + PPU_CLUS1CORE6_IRQ = 96, /* Cluster 1 Core 6 Power Policy Unit */ + PPU_CLUS1CORE7_IRQ = 97, /* Cluster 1 Core 7 Power Policy Unit */ + PLL_CLUS0_LOCK_IRQ = 98, /* Cluster 0 CPU PLL Lock */ + PLL_CLUS1_LOCK_IRQ = 99, /* Cluster 1 CPU PLL Lock */ + PLL_GPU_LOCK_IRQ = 100, /* GPU PLL Lock */ + PLL_VPU_LOCK_IRQ = 101, /* Video PLL Lock */ + PLL_SYS_LOCK_IRQ = 102, /* System PLL Lock */ + PLL_DPU_LOCK_IRQ = 103, /* Display PLL Lock */ + PLL_CLUS0CORE0_IRQ = 104, /* Cluster 0 PLL0 Lock */ + PLL_CLUS0CORE1_IRQ = 105, /* Cluster 0 PLL1 Lock */ + PLL_CLUS0CORE2_IRQ = 106, /* Cluster 0 PLL2 Lock */ + PLL_CLUS0CORE3_IRQ = 107, /* Cluster 0 PLL3 Lock */ + PLL_CLUS0CORE4_IRQ = 108, /* Cluster 0 PLL4 Lock */ + PLL_CLUS0CORE5_IRQ = 109, /* Cluster 0 PLL5 Lock */ + PLL_CLUS0CORE6_IRQ = 110, /* Cluster 0 PLL6 Lock */ + PLL_CLUS0CORE7_IRQ = 111, /* Cluster 0 PLL7 Lock */ + PLL_CLUS1CORE0_IRQ = 112, /* Cluster 1 PLL0 Lock */ + PLL_CLUS1CORE1_IRQ = 113, /* Cluster 1 PLL1 Lock */ + PLL_CLUS1CORE2_IRQ = 114, /* Cluster 1 PLL2 Lock */ + PLL_CLUS1CORE3_IRQ = 115, /* Cluster 1 PLL3 Lock */ + PLL_CLUS1CORE4_IRQ = 116, /* Cluster 1 PLL4 Lock */ + PLL_CLUS1CORE5_IRQ = 117, /* Cluster 1 PLL5 Lock */ + PLL_CLUS1CORE6_IRQ = 118, /* Cluster 1 PLL6 Lock */ + PLL_CLUS1CORE7_IRQ = 119, /* Cluster 1 PLL7 Lock */ + DBG_PWR_REQ0_IRQ = 120, /* Debug power request 0 */ + DBG_PWR_REQ1_IRQ = 121, /* Debug power request 1 */ + DBG_PWR_REQ2_IRQ = 122, /* Debug power request 2 */ + DBG_PWR_REQ3_IRQ = 123, /* Debug power request 3 */ + DBG_RST_REQ_IRQ = 124, /* Debug reset request */ + SYS_PWR_REQ0_IRQ = 125, /* System power request 0 */ + SYS_PWR_REQ1_IRQ = 126, /* System power request 1 */ + SYS_PWR_REQ2_IRQ = 127, /* System power request 2 */ + SYS_PWR_REQ3_IRQ = 128, /* System power request 3 */ + SYS_RST_REQ_IRQ = 129, /* System reset request */ + DBG_CHN_PWRUP_IRQ = 130, /* Debug chain power up */ + RESERVED131_IRQ = 131, /* Reserved */ + RESERVED132_IRQ = 132, /* Reserved */ + RESERVED133_IRQ = 133, /* Reserved */ + RESERVED134_IRQ = 134, /* Reserved */ + RESERVED135_IRQ = 135, /* Reserved */ + RESERVED136_IRQ = 136, /* Reserved */ + RESERVED137_IRQ = 137, /* Reserved */ + RESERVED138_IRQ = 138, /* Reserved */ + RESERVED139_IRQ = 139, /* Reserved */ + RESERVED140_IRQ = 140, /* Reserved */ + RESERVED141_IRQ = 141, /* Reserved */ + RESERVED142_IRQ = 142, /* Reserved */ + RESERVED143_IRQ = 143, /* Reserved */ + RESERVED144_IRQ = 144, /* Reserved */ + RESERVED145_IRQ = 145, /* Reserved */ + RESERVED146_IRQ = 146, /* Reserved */ + RESERVED147_IRQ = 147, /* Reserved */ + RESERVED148_IRQ = 148, /* Reserved */ + RESERVED149_IRQ = 149, /* Reserved */ + RESERVED150_IRQ = 150, /* Reserved */ + RESERVED151_IRQ = 151, /* Reserved */ + RESERVED152_IRQ = 152, /* Reserved */ + RESERVED153_IRQ = 153, /* Reserved */ + RESERVED154_IRQ = 154, /* Reserved */ + RESERVED155_IRQ = 155, /* Reserved */ + RESERVED156_IRQ = 156, /* Reserved */ + RESERVED157_IRQ = 157, /* Reserved */ + RESERVED158_IRQ = 158, /* Reserved */ + RESERVED159_IRQ = 159, /* Reserved */ + SCP_EXT_INTR0_IRQ = 160, /* SCP Customer Extension */ + SCP_EXT_INTR1_IRQ = 161, /* SCP Customer Extension */ + SCP_EXT_INTR2_IRQ = 162, /* SCP Customer Extension */ + SCP_EXT_INTR3_IRQ = 163, /* SCP Customer Extension */ + SCP_EXT_INTR4_IRQ = 164, /* SCP Customer Extension */ + SCP_EXT_INTR5_IRQ = 165, /* SCP Customer Extension */ + SCP_EXT_INTR6_IRQ = 166, /* SCP Customer Extension */ + SCP_EXT_INTR7_IRQ = 167, /* SCP Customer Extension */ + SCP_EXT_INTR8_IRQ = 168, /* SCP Customer Extension */ + SCP_EXT_INTR9_IRQ = 169, /* SCP Customer Extension */ + SCP_EXT_INTR10_IRQ = 170, /* SCP Customer Extension */ + SCP_EXT_INTR11_IRQ = 171, /* SCP Customer Extension */ + SCP_EXT_INTR12_IRQ = 172, /* SCP Customer Extension */ + SCP_EXT_INTR13_IRQ = 173, /* SCP Customer Extension */ + SCP_EXT_INTR14_IRQ = 174, /* SCP Customer Extension */ + SCP_EXT_INTR15_IRQ = 175, /* SCP Customer Extension */ + SCP_EXT_INTR16_IRQ = 176, /* SCP Customer Extension */ + SCP_EXT_INTR17_IRQ = 177, /* SCP Customer Extension */ + SCP_EXT_INTR18_IRQ = 178, /* SCP Customer Extension */ + SCP_EXT_INTR19_IRQ = 179, /* SCP Customer Extension */ + SCP_EXT_INTR20_IRQ = 180, /* SCP Customer Extension */ + SCP_EXT_INTR21_IRQ = 181, /* SCP Customer Extension */ + SCP_EXT_INTR22_IRQ = 182, /* SCP Customer Extension */ + SCP_EXT_INTR23_IRQ = 183, /* SCP Customer Extension */ + SCP_EXT_INTR24_IRQ = 184, /* SCP Customer Extension */ + SCP_EXT_INTR25_IRQ = 185, /* SCP Customer Extension */ + SCP_EXT_INTR26_IRQ = 186, /* SCP Customer Extension */ + SCP_EXT_INTR27_IRQ = 187, /* SCP Customer Extension */ + SCP_EXT_INTR28_IRQ = 188, /* SCP Customer Extension */ + SCP_EXT_INTR29_IRQ = 189, /* SCP Customer Extension */ + SCP_EXT_INTR30_IRQ = 190, /* SCP Customer Extension */ + SCP_EXT_INTR31_IRQ = 191, /* SCP Customer Extension */ +}; + +#endif /* SGM776_IRQ_H */ diff --git a/product/sgm776/include/sgm776_mhu.h b/product/sgm776/include/sgm776_mhu.h new file mode 100644 index 00000000..6ec8101a --- /dev/null +++ b/product/sgm776/include/sgm776_mhu.h @@ -0,0 +1,21 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + * + * Description: + * MHU module device indexes. + */ + +#ifndef SGM776_MHU_H +#define SGM776_MHU_H + +enum sgm776_mhu_device_idx { + SGM776_MHU_DEVICE_IDX_S, + SGM776_MHU_DEVICE_IDX_NS_H, + SGM776_MHU_DEVICE_IDX_NS_L, + SGM776_MHU_DEVICE_IDX_COUNT +}; + +#endif /* SGM776_MHU_H */ diff --git a/product/sgm776/include/sgm776_mmap.h b/product/sgm776/include/sgm776_mmap.h new file mode 100644 index 00000000..9ae9f58a --- /dev/null +++ b/product/sgm776/include/sgm776_mmap.h @@ -0,0 +1,96 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef SGM776_MMAP_H +#define SGM776_MMAP_H + +#include <stdint.h> + +/* + * Top-level base addresses + */ +#define EXPANSION0_BASE UINT32_C(0x40000000) +#define PERIPHERAL_BASE UINT32_C(0x44000000) +#define POWER_PERIPHERAL_BASE UINT32_C(0x50000000) +#define SYS0_BASE UINT32_C(0x60000000) +#define SYS1_BASE UINT32_C(0xA0000000) +#define PPB_INTERNAL_BASE UINT32_C(0xE0000000) +#define PPB_EXTERNAL_BASE UINT32_C(0xE0040000) +#define EXPANSION1_BASE UINT32_C(0xE0100000) + +/* + * Peripherals + */ +#define REFCLK_CNTCTL_BASE (PERIPHERAL_BASE + 0x0000) +#define REFCLK_CNTBASE0_BASE (PERIPHERAL_BASE + 0x1000) +#define MHU_RECV_NS_BASE (PERIPHERAL_BASE + 0x2000) +#define MHU_SEND_NS_BASE (PERIPHERAL_BASE + 0x3000) +#define MHU_RECV_S_BASE (PERIPHERAL_BASE + 0x4000) +#define MHU_SEND_S_BASE (PERIPHERAL_BASE + 0x5000) +#define WDOG_BASE (PERIPHERAL_BASE + 0x6000) +#define S32K_CNTCONTROL_BASE (PERIPHERAL_BASE + 0x7000) +#define S32K_CNTCTL_BASE (PERIPHERAL_BASE + 0x8000) +#define S32K_CNTBASE0_BASE (PERIPHERAL_BASE + 0x9000) +#define CS_CNTCONTROL_BASE (PERIPHERAL_BASE + 0xA000) + +/* + * Power control peripherals + */ +#define PIK_SCP_BASE (POWER_PERIPHERAL_BASE + 0x000000) +#define PIK_DEBUG_BASE (POWER_PERIPHERAL_BASE + 0x020000) +#define SENSOR_DEBUG_BASE (POWER_PERIPHERAL_BASE + 0x030000) +#define PIK_SYSTEM_BASE (POWER_PERIPHERAL_BASE + 0x040000) +#define SENSOR_SYSTEM_BASE (POWER_PERIPHERAL_BASE + 0x050000) +#define PIK_CLUS0_BASE (POWER_PERIPHERAL_BASE + 0x060000) +#define SENSOR_CLUS0_BASE (POWER_PERIPHERAL_BASE + 0x070000) +#define PIK_CLUS1_BASE (POWER_PERIPHERAL_BASE + 0x080000) +#define SENSOR_CLUS1_BASE (POWER_PERIPHERAL_BASE + 0x090000) +#define PIK_GPU_BASE (POWER_PERIPHERAL_BASE + 0x0A0000) +#define SENSOR_GPU_BASE (POWER_PERIPHERAL_BASE + 0x0B0000) +#define PIK_VPU_BASE (POWER_PERIPHERAL_BASE + 0x0C0000) +#define SENSOR_VPU_BASE (POWER_PERIPHERAL_BASE + 0x0D0000) +#define PIK_DPU_BASE (POWER_PERIPHERAL_BASE + 0x0E0000) +#define SENSOR_DPU_BASE (POWER_PERIPHERAL_BASE + 0x0F0000) +#define PIK_DEBUG_CHAIN_BASE (POWER_PERIPHERAL_BASE + 0x100000) + +/* + * PPU base address + */ +#define PPU_SCP_BASE (PIK_SCP_BASE + 0x1000) +#define PPU_SYS0_BASE (PIK_SYSTEM_BASE + 0x1000) +#define PPU_SYS1_BASE (PIK_SYSTEM_BASE + 0x2000) +#define PPU_DEBUG_BASE (PIK_DEBUG_BASE + 0x1000) +#define PPU_CLUS0CORE0_BASE (PIK_CLUS0_BASE + 0x2000) +#define PPU_CLUS0CORE1_BASE (PIK_CLUS0_BASE + 0x3000) +#define PPU_CLUS0CORE2_BASE (PIK_CLUS0_BASE + 0x4000) +#define PPU_CLUS0CORE3_BASE (PIK_CLUS0_BASE + 0x5000) +#define PPU_CLUS0CORE4_BASE (PIK_CLUS0_BASE + 0x6000) +#define PPU_CLUS0CORE5_BASE (PIK_CLUS0_BASE + 0x7000) +#define PPU_CLUS0CORE6_BASE (PIK_CLUS0_BASE + 0x8000) +#define PPU_CLUS0CORE7_BASE (PIK_CLUS0_BASE + 0x9000) +#define PPU_CLUS0_BASE (PIK_CLUS0_BASE + 0x1000) +#define PPU_CLUS1CORE0_BASE (PIK_CLUS1_BASE + 0x2000) +#define PPU_CLUS1CORE1_BASE (PIK_CLUS1_BASE + 0x3000) +#define PPU_CLUS1CORE2_BASE (PIK_CLUS1_BASE + 0x4000) +#define PPU_CLUS1CORE3_BASE (PIK_CLUS1_BASE + 0x5000) +#define PPU_CLUS1_BASE (PIK_CLUS1_BASE + 0x1000) +#define PPU_GPU_BASE (PIK_GPU_BASE + 0x1000) +#define PPU_VPU_BASE (PIK_VPU_BASE + 0x1000) +#define PPU_DPU_BASE (PIK_DPU_BASE + 0x1000) + +/* + * System access port 1 + */ +#define TRUSTED_RAM_BASE (SYS1_BASE + 0x04000000) +#define NONTRUSTED_RAM_BASE (SYS1_BASE + 0x06000000) +#define CCI_BASE (SYS1_BASE + 0x2A000000) +#define ARACHNE_BASE (SYS1_BASE + 0x2A100000) +#define SID_BASE (SYS1_BASE + 0x2A420000) +#define REFCLK_CNTCONTROL_BASE (SYS1_BASE + 0x2A430000) +#define DMC_BASE (SYS1_BASE + 0x2A500000) + +#endif /* SGM776_MMAP_H */ diff --git a/product/sgm776/include/sgm776_mmap_scp.h b/product/sgm776/include/sgm776_mmap_scp.h new file mode 100644 index 00000000..147b1f16 --- /dev/null +++ b/product/sgm776/include/sgm776_mmap_scp.h @@ -0,0 +1,19 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + * + * Description: + * SCP ROM and RAM memory bases. These definitions are kept isolated without + * the UINT32_C() or UL decorators allowing them to be used in the linker + * script. + */ + +#ifndef SGM776_MMAP_SCP_H +#define SGM776_MMAP_SCP_H + +#define SCP_ROM_BASE 0x00000000 +#define SCP_RAM_BASE 0x10000000 + +#endif /* SGM776_MMAP_SCP_H */ diff --git a/product/sgm776/include/sgm776_pik.h b/product/sgm776/include/sgm776_pik.h new file mode 100644 index 00000000..bdb57c11 --- /dev/null +++ b/product/sgm776/include/sgm776_pik.h @@ -0,0 +1,29 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef SGM776_PIK_H +#define SGM776_PIK_H + +#include <sgm776_mmap.h> +#include <sgm776_pik_cpu.h> +#include <sgm776_pik_debug.h> +#include <sgm776_pik_dpu.h> +#include <sgm776_pik_scp.h> +#include <sgm776_pik_gpu.h> +#include <sgm776_pik_system.h> +#include <sgm776_pik_vpu.h> + +#define PIK_CLUS0 ((struct pik_cpu_reg *) PIK_CLUS0_BASE) +#define PIK_CLUS1 ((struct pik_cpu_reg *) PIK_CLUS1_BASE) +#define PIK_DEBUG ((struct pik_debug_reg *) PIK_DEBUG_BASE) +#define PIK_DPU ((struct pik_dpu_reg *) PIK_DPU_BASE) +#define PIK_GPU ((struct pik_gpu_reg *) PIK_GPU_BASE) +#define PIK_SCP ((struct pik_scp_reg *) PIK_SCP_BASE) +#define PIK_SYSTEM ((struct pik_system_reg *) PIK_SYSTEM_BASE) +#define PIK_VPU ((struct pik_vpu_reg *) PIK_VPU_BASE) + +#endif /* SGM776_PIK_H */ diff --git a/product/sgm776/include/sgm776_pik_cpu.h b/product/sgm776/include/sgm776_pik_cpu.h new file mode 100644 index 00000000..34cdd146 --- /dev/null +++ b/product/sgm776/include/sgm776_pik_cpu.h @@ -0,0 +1,94 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef SGM776_PIK_CPU_H +#define SGM776_PIK_CPU_H + +#include <stdint.h> +#include <fwk_macros.h> + +#define PE_COUNT_MAX 16 + +/*! + * \brief PE Static Configuration register definitions + */ +struct static_config_reg { + FWK_RW uint32_t STATIC_CONFIG; + FWK_RW uint32_t RVBARADDR_LW; + FWK_RW uint32_t RVBARADDR_UP; + uint32_t RESERVED; +}; + +/*! + * \brief AP cores clock control register definitions + */ +struct coreclk_reg { + FWK_RW uint32_t CTRL; + FWK_RW uint32_t DIV; + uint32_t RESERVED; + FWK_RW uint32_t MOD; +}; + +/*! + * \brief CPU (v8.2) PIK register definitions + */ +struct pik_cpu_reg { + FWK_RW uint32_t CLUSTER_CONFIG; + uint8_t RESERVED0[0x10 - 0x4]; + struct static_config_reg STATIC_CONFIG[PE_COUNT_MAX]; + uint8_t RESERVED1[0x800 - 0x110]; + FWK_RW uint32_t PPUCLK_CTRL; + FWK_RW uint32_t PPUCLK_DIV1; + uint8_t RESERVED2[0x810 - 0x808]; + FWK_RW uint32_t PCLK_CTRL; + uint8_t RESERVED3[0x820 - 0x814]; + FWK_RW uint32_t DBGCLK_CTRL; + FWK_RW uint32_t DBGCLK_DIV1; + uint8_t RESERVED4[0x830 - 0x828]; + FWK_RW uint32_t GICCLK_CTRL; + uint8_t RESERVED5[0x840 - 0x834]; + FWK_RW uint32_t AMBACLK_CTRL; + uint8_t RESERVED6[0x850 - 0x844]; + FWK_RW uint32_t CLUSCLK_CTRL; + FWK_RW uint32_t CLUSCLK_DIV1; + uint8_t RESERVED7[0x860 - 0x858]; + struct coreclk_reg CORECLK[PE_COUNT_MAX]; + uint8_t RESERVED8[0xA00 - 0x960]; + FWK_R uint32_t CLKFORCE_STATUS; + FWK_RW uint32_t CLKFORCE_SET; + FWK_RW uint32_t CLKFORCE_CLR; + uint8_t RESERVED9[0xB00 - 0xA0C]; + FWK_R uint32_t NERRIQ_INT_STATUS; + FWK_R uint32_t NFAULTIQ_INT_STATUS; + uint8_t RESERVED10[0xFB4 - 0xB08]; + FWK_R uint32_t CAP3; + FWK_R uint32_t CAP2; + FWK_R uint32_t CAP; + FWK_R uint32_t PCL_CONFIG; + uint8_t RESERVED11[0xFD0 - 0xFC4]; + FWK_R uint32_t PID4; + FWK_R uint32_t PID5; + FWK_R uint32_t PID6; + FWK_R uint32_t PID7; + FWK_R uint32_t PID0; + FWK_R uint32_t PID1; + FWK_R uint32_t PID2; + FWK_R uint32_t PID3; + FWK_R uint32_t ID0; + FWK_R uint32_t ID1; + FWK_R uint32_t ID2; + FWK_R uint32_t ID3; +}; + +#define PIK_CPU_CAP_CLUSSYNC UINT32_C(0x00000001) +#define PIK_CPU_CAP_CORESYNC(CORE) ((uint32_t)(1 << ((CORE) + 1))) +#define PIK_CPU_CAP_PE_MASK UINT32_C(0xF0000000) +#define PIK_CPU_CAP_PE_POS 28 + +#define PIK_CPU_PCL_CONFIG_NO_OF_PPU UINT32_C(0x0000000F) + +#endif /* SGM776_PIK_CPU_H */ diff --git a/product/sgm776/include/sgm776_pik_debug.h b/product/sgm776/include/sgm776_pik_debug.h new file mode 100644 index 00000000..5421fae9 --- /dev/null +++ b/product/sgm776/include/sgm776_pik_debug.h @@ -0,0 +1,65 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef SGM776_PIK_DEBUG_H +#define SGM776_PIK_DEBUG_H + +#include <stdint.h> +#include <fwk_macros.h> + +/*! + * \brief Debug register definitions + */ +struct pik_debug_reg { + FWK_R uint32_t DBG_PWR_REQ_ST[4]; + FWK_R uint32_t DBG_PWR_REQ_ACK[4]; + FWK_R uint32_t DBG_RST_REQ_ST; + FWK_R uint32_t DBG_RST_ACK; + uint8_t RESERVED0[0x30 - 0x28]; + FWK_R uint32_t SYS_PWR_REQ_ST[4]; + FWK_R uint32_t SYS_PWR_REQ_ACK[4]; + FWK_R uint32_t SYS_RST_REQ_ST; + uint8_t RESERVED1[0x60 - 0x54]; + FWK_RW uint32_t DEBUG_CONFIG; + uint8_t RESERVED2[0x810 - 0x64]; + FWK_RW uint32_t TRACECLK_CTRL; + FWK_RW uint32_t TRACECLK_DIV1; + uint8_t RESERVED3[0x820 - 0x818]; + FWK_RW uint32_t PCLKDBG_CTRL; + FWK_RW uint32_t PCLKDBG_DIV1; + uint8_t RESERVED4[0x830 - 0x828]; + FWK_RW uint32_t DBGCLK_CTRL; + FWK_RW uint32_t DBGCLK_DIV1; + uint8_t RESERVED5[0xA00 - 0x838]; + FWK_R uint32_t CLKFORCE_STATUS; + FWK_RW uint32_t CLKFORCE_SET; + FWK_RW uint32_t CLKFORCE_CLR; + uint8_t RESERVED6[0xB00 - 0xA0C]; + FWK_R uint32_t DBG_PWR_REQ_INT_ST[4]; + FWK_R uint32_t DBG_RST_REQ_INT_ST; + uint8_t RESERVED7[0xB20 - 0xB14]; + FWK_R uint32_t SYS_PWR_REQ_INT_ST[4]; + FWK_R uint32_t SYS_RST_REQ_INT_ST; + uint8_t RESERVED8[0xFBC - 0xB34]; + FWK_R uint32_t CAP; + FWK_R uint32_t PCL_CONFIG; + uint8_t RESERVED9[0xFD0 - 0xFC4]; + FWK_R uint32_t PID4; + FWK_R uint32_t PID5; + FWK_R uint32_t PID6; + FWK_R uint32_t PID7; + FWK_R uint32_t PID0; + FWK_R uint32_t PID1; + FWK_R uint32_t PID2; + FWK_R uint32_t PID3; + FWK_R uint32_t ID0; + FWK_R uint32_t ID1; + FWK_R uint32_t ID2; + FWK_R uint32_t ID3; +}; + +#endif /* SGM776_PIK_DEBUG_H */ diff --git a/product/sgm776/include/sgm776_pik_dpu.h b/product/sgm776/include/sgm776_pik_dpu.h new file mode 100644 index 00000000..fd3ebdce --- /dev/null +++ b/product/sgm776/include/sgm776_pik_dpu.h @@ -0,0 +1,43 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef SGM776_PIK_DPU_H +#define SGM776_PIK_DPU_H + +#include <stdint.h> +#include <fwk_macros.h> + +/*! + * \brief DPU PIK register definitions + */ +struct pik_dpu_reg { + FWK_R uint8_t RESERVED0[0x830]; + FWK_RW uint32_t ACLKDP_CTRL; + FWK_RW uint32_t ACLKDP_DIV1; + FWK_RW uint32_t ACLKDP_DIV2; + uint8_t RESERVED3[0xA00 - 0x83C]; + FWK_R uint32_t CLKFORCE_STATUS; + FWK_W uint32_t CLKFORCE_SET; + FWK_W uint32_t CLKFORCE_CLR; + uint8_t RESERVED4[0xFC0 - 0xA0C]; + FWK_RW uint32_t PCL_CONFIG; + uint8_t RESERVED5[0xFD0 - 0xFC4]; + FWK_R uint32_t PID4; + FWK_R uint32_t PID5; + FWK_R uint32_t PID6; + FWK_R uint32_t PID7; + FWK_R uint32_t PID0; + FWK_R uint32_t PID1; + FWK_R uint32_t PID2; + FWK_R uint32_t PID3; + FWK_R uint32_t ID0; + FWK_R uint32_t ID1; + FWK_R uint32_t ID2; + FWK_R uint32_t ID3; +}; + +#endif /* SGM776_PIK_DPU_H */ diff --git a/product/sgm776/include/sgm776_pik_gpu.h b/product/sgm776/include/sgm776_pik_gpu.h new file mode 100644 index 00000000..f10af96b --- /dev/null +++ b/product/sgm776/include/sgm776_pik_gpu.h @@ -0,0 +1,45 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef SGM776_PIK_GPU_H +#define SGM776_PIK_GPU_H + +#include <stdint.h> +#include <fwk_macros.h> + +/*! + * \brief GPU PIK register definitions + */ +struct pik_gpu_reg { + uint8_t RESERVED0[0x810]; + FWK_RW uint32_t GPUCLK_CTRL; + FWK_RW uint32_t GPUCLK_DIV1; + FWK_RW uint32_t GPUCLK_DIV2; + uint8_t RESERVED1[0x820 - 0x81C]; + FWK_RW uint32_t ACLKGPU_CTRL; + uint8_t RESERVED2[0xA00 - 0x824]; + FWK_R uint32_t CLKFORCE_STATUS; + FWK_W uint32_t CLKFORCE_SET; + FWK_W uint32_t CLKFORCE_CLR; + uint8_t RESERVED3[0xFBC - 0xA0C]; + FWK_R uint32_t CAP; + FWK_R uint32_t PCL_CONFIG; + uint8_t RESERVED4[0xFD0 - 0xFC4]; + FWK_R uint32_t PID4; + FWK_R uint32_t PID5; + FWK_R uint32_t PID6; + FWK_R uint32_t PID7; + FWK_R uint32_t PID0; + FWK_R uint32_t PID1; + FWK_R uint32_t PID2; + FWK_R uint32_t PID3; + FWK_R uint32_t ID0; + FWK_R uint32_t ID1; + FWK_R uint32_t ID2; + FWK_R uint32_t ID3; +}; +#endif /* SGM776_PIK_GPU_H */ diff --git a/product/sgm776/include/sgm776_pik_scp.h b/product/sgm776/include/sgm776_pik_scp.h new file mode 100644 index 00000000..ae2258db --- /dev/null +++ b/product/sgm776/include/sgm776_pik_scp.h @@ -0,0 +1,61 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef SGM776_PIK_SCP_H +#define SGM776_PIK_SCP_H + +#include <stdint.h> +#include <fwk_macros.h> + +/*! + * \brief SCP PIK register definitions + */ +struct pik_scp_reg { + uint8_t RESERVED0[0x10]; + FWK_RW uint32_t RESET_SYNDROME; + FWK_RW uint32_t WIC_CTRL; + FWK_R uint32_t WIC_STATUS; + uint8_t RESERVED1[0xA00 - 0x1C]; + FWK_R uint32_t CLKFORCE_STATUS; + FWK_RW uint32_t CLKFORCE_SET; + FWK_RW uint32_t CLKFORCE_CLR; + uint32_t RESERVED2; + FWK_R uint32_t PLL_STATUS0; + FWK_R uint32_t PLL_STATUS1; + uint8_t RESERVED3[0xFC0 - 0xA18]; + FWK_R uint32_t PCL_CONFIG; + uint8_t RESERVED4[0xFD0 - 0xFC4]; + FWK_R uint32_t PID4; + FWK_R uint32_t PID5; + FWK_R uint32_t PID6; + FWK_R uint32_t PID7; + FWK_R uint32_t PID0; + FWK_R uint32_t PID1; + FWK_R uint32_t PID2; + FWK_R uint32_t PID3; + FWK_R uint32_t ID0; + FWK_R uint32_t ID1; + FWK_R uint32_t ID2; + FWK_R uint32_t ID3; +}; + +#define PLL_STATUS0_REFCLK UINT32_C(0x00000001) +#define PLL_STATUS0_GPUPLLLOCK UINT32_C(0x00000008) +#define PLL_STATUS0_VIDEOPLLLOCK UINT32_C(0x00000010) +#define PLL_STATUS0_SYSPLLLOCK UINT32_C(0x00000020) +#define PLL_STATUS0_DISPLAYPLLLOCK UINT32_C(0x00000040) + +#define PLL_STATUS1_CPUPLLLOCK(CORE, PLL) \ + ((uint32_t)((1 << (PLL)) << ((CORE) * 8))) + +#define RESET_SYNDROME_PORESET UINT32_C(0x01) +#define RESET_SYNDROME_WDOGRESET_SCP UINT32_C(0x02) +#define RESET_SYNDROME_WDOGRESET_SYS UINT32_C(0x04) +#define RESET_SYNDROME_SYSRESETREQ UINT32_C(0x08) +#define RESET_SYNDROME_SCPM3LOCKUP UINT32_C(0x10) + +#endif /* SGM776_PIK_SCP_H */ diff --git a/product/sgm776/include/sgm776_pik_system.h b/product/sgm776/include/sgm776_pik_system.h new file mode 100644 index 00000000..3099713b --- /dev/null +++ b/product/sgm776/include/sgm776_pik_system.h @@ -0,0 +1,69 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef SGM776_PIK_SYSTEM_H +#define SGM776_PIK_SYSTEM_H + +#include <stdint.h> +#include <fwk_macros.h> + +/*! + * \brief System PIK register definitions + */ +struct pik_system_reg { + uint8_t RESERVED0[0x800]; + FWK_RW uint32_t PPUCLK_CTRL; + FWK_RW uint32_t PPUCLK_DIV1; + uint8_t RESERVED1[0x810 - 0x808]; + FWK_RW uint32_t NOCMEMCLK_CTRL; + FWK_RW uint32_t NOCMEMCLK_DIV1; + uint8_t RESERVED2[0x820 - 0x818]; + FWK_RW uint32_t ACLKCCI_CTRL; + FWK_RW uint32_t ACLKCCI_DIV1; + uint8_t RESERVED3[0x840 - 0x828]; + FWK_RW uint32_t TCUCLK_CTRL; + FWK_RW uint32_t TCUCLK_DIV1; + uint8_t RESERVED4[0x850 - 0x848]; + FWK_RW uint32_t GICCLK_CTRL; + FWK_RW uint32_t GICCLK_DIV1; + uint8_t RESERVED5[0x860 - 0x858]; + FWK_RW uint32_t PCLKSCP_CTRL; + FWK_RW uint32_t PCLKSCP_DIV1; + uint8_t RESERVED6[0x870 - 0x868]; + FWK_RW uint32_t SYSPERCLK_CTRL; + FWK_RW uint32_t SYSPERCLK_DIV1; + uint8_t RESERVED7[0x880 - 0x878]; + FWK_RW uint32_t FCMCLK_CTRL; + FWK_RW uint32_t FCMCLK_DIV1; + uint8_t RESERVED8[0xA00 - 0x888]; + FWK_R uint32_t CLKFORCE_STATUS; + FWK_RW uint32_t CLKFORCE_SET; + FWK_RW uint32_t CLKFORCE_CLR; + uint8_t RESERVED9[0xFBC - 0xA0C]; + FWK_R uint32_t CAP; + FWK_R uint32_t PCL_CONFIG; + uint8_t RESERVED10[0xFD0 - 0xFC4]; + FWK_R uint32_t PID4; + FWK_R uint32_t PID5; + FWK_R uint32_t PID6; + FWK_R uint32_t PID7; + FWK_R uint32_t PID0; + FWK_R uint32_t PID1; + FWK_R uint32_t PID2; + FWK_R uint32_t PID3; + FWK_R uint32_t ID0; + FWK_R uint32_t ID1; + FWK_R uint32_t ID2; + FWK_R uint32_t ID3; +}; + +#define CAP_GICCLK_GATING_SUPPORT UINT32_C(0x00000001) +#define CAP_TCUCLK_SUPPORT UINT32_C(0x00000002) +#define CAP_ELA_SUPPORT UINT32_C(0x00000004) +#define CAP_FCMCLK_SUPPORT UINT32_C(0x00000008) + +#endif /* SGM776_PIK_SYSTEM_H */ diff --git a/product/sgm776/include/sgm776_pik_vpu.h b/product/sgm776/include/sgm776_pik_vpu.h new file mode 100644 index 00000000..66269146 --- /dev/null +++ b/product/sgm776/include/sgm776_pik_vpu.h @@ -0,0 +1,43 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef SGM776_PIK_VPU_H +#define SGM776_PIK_VPU_H + +#include <stdint.h> +#include <fwk_macros.h> + +/*! + * \brief VPU PIK register definitions + */ +struct pik_vpu_reg { + uint8_t RESERVED0[0x810]; + FWK_RW uint32_t VIDEOCLK_CTRL; + FWK_RW uint32_t VIDEOCLK_DIV1; + FWK_RW uint32_t VIDEOCLK_DIV2; + uint8_t RESERVED1[0xA00 - 0x81C]; + FWK_R uint32_t CLKFORCE_STATUS; + FWK_W uint32_t CLKFORCE_SET; + FWK_W uint32_t CLKFORCE_CLR; + uint8_t RESERVED2[0xFC0 - 0xA0C]; + FWK_R uint32_t PCL_CONFIG; + uint8_t RESERVED3[0xFD0 - 0xFC4]; + FWK_R uint32_t PID4; + FWK_R uint32_t PID5; + FWK_R uint32_t PID6; + FWK_R uint32_t PID7; + FWK_R uint32_t PID0; + FWK_R uint32_t PID1; + FWK_R uint32_t PID2; + FWK_R uint32_t PID3; + FWK_R uint32_t ID0; + FWK_R uint32_t ID1; + FWK_R uint32_t ID2; + FWK_R uint32_t ID3; +}; + +#endif /* SGM776_PIK_VPU_H */ diff --git a/product/sgm776/include/sgm776_scmi.h b/product/sgm776/include/sgm776_scmi.h new file mode 100644 index 00000000..b06607f1 --- /dev/null +++ b/product/sgm776/include/sgm776_scmi.h @@ -0,0 +1,29 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + * + * Description: + * Definitions for SCMI and SMT module configurations. + */ + +#ifndef SGM776_SCMI_H +#define SGM776_SCMI_H + +/* SCMI agent identifiers */ +enum sgm776_scmi_agent_id { + /* 0 is reserved for the platform */ + SCMI_AGENT_ID_OSPM = 1, + SCMI_AGENT_ID_PSCI, + SCMI_AGENT_ID_COUNT +}; + +/* SCMI service indexes */ +enum sgm776_scmi_service_idx { + SGM776_SCMI_SERVICE_IDX_PSCI, + SGM776_SCMI_SERVICE_IDX_OSPM_0, + SGM776_SCMI_SERVICE_IDX_OSPM_1, + SGM776_SCMI_SERVICE_IDX_COUNT, +}; +#endif /* SGM776_SCMI_H */ diff --git a/product/sgm776/include/sgm776_sds.h b/product/sgm776/include/sgm776_sds.h new file mode 100644 index 00000000..b3da4fe7 --- /dev/null +++ b/product/sgm776/include/sgm776_sds.h @@ -0,0 +1,149 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef SGM776_SDS_H +#define SGM776_SDS_H + +#include <mod_sds.h> + +/* + * Structure identifiers. + */ +enum sgm776_sds_struct_id { + SGM776_SDS_CPU_INFO = 1 | (1 << MOD_SDS_ID_VERSION_MAJOR_POS), + SGM776_SDS_ROM_VERSION = 2 | (1 << MOD_SDS_ID_VERSION_MAJOR_POS), + SGM776_SDS_RAM_VERSION = 3 | (1 << MOD_SDS_ID_VERSION_MAJOR_POS), + SGM776_SDS_PLATFORM_ID = 4 | (1 << MOD_SDS_ID_VERSION_MAJOR_POS), + SGM776_SDS_RESET_SYNDROME = 5 | (1 << MOD_SDS_ID_VERSION_MAJOR_POS), + SGM776_SDS_FEATURE_AVAILABILITY = 6 | (1 << MOD_SDS_ID_VERSION_MAJOR_POS), + SGM776_SDS_CPU_BOOTCTR = 7 | (1 << MOD_SDS_ID_VERSION_MAJOR_POS), + SGM776_SDS_CPU_FLAGS = 8 | (1 << MOD_SDS_ID_VERSION_MAJOR_POS), + SGM776_SDS_BOOTLOADER = 9 | (1 << MOD_SDS_ID_VERSION_MAJOR_POS), +}; + +/* + * Structure sizes. + */ +#define SGM776_SDS_CPU_INFO_SIZE 4 +#define SGM776_SDS_ROM_VERSION_SIZE 4 +#define SGM776_SDS_RAM_VERSION_SIZE 4 +#define SGM776_SDS_PLATFORM_ID_SIZE 8 +#define SGM776_SDS_RESET_SYNDROME_SIZE 4 +#define SGM776_SDS_FEATURE_AVAILABILITY_SIZE 4 +#define SGM776_SDS_CPU_BOOTCTR_SIZE 8 +#define SGM776_SDS_CPU_FLAGS_SIZE 8 +#define SGM776_SDS_BOOTLOADER_SIZE 12 + +/* + * Field masks and offsets for the SGM776_SDS_AP_CPU_INFO structure. + */ +#define SGM776_SDS_CPU_INFO_PRIMARY_MASK 0xFFFFFFFF +#define SGM776_SDS_CPU_INFO_PRIMARY_POS 0 + +/* + * Structure, field masks and offsets for the SGM776_SDS_PLATFORM_ID structure. + */ + +struct sgm776_sds_platid { + uint32_t platform_identifier; + uint32_t platform_type_identifier; +}; + +#define SGM776_SDS_PLATID_PARTNO_MASK 0xFFF +#define SGM776_SDS_PLATID_DESIGNER_MASK 0xFF000 +#define SGM776_SDS_PLATID_REV_MINOR_MASK 0xF00000 +#define SGM776_SDS_PLATID_REV_MAJOR_MASK 0xF000000 +#define SGM776_SDS_PLATID_CONFIG_MASK 0xF0000000 +#define SGM776_SDS_PLATID_TYPE_MASK 0xF + +#define SGM776_SDS_PLATID_PARTNO_POS 0 +#define SGM776_SDS_PLATID_DESIGNER_POS 12 +#define SGM776_SDS_PLATID_REV_MINOR_POS 20 +#define SGM776_SDS_PLATID_REV_MAJOR_POS 24 +#define SGM776_SDS_PLATID_CONFIG_POS 28 + +#define SGM776_SDS_PLATID_TYPE_POS 0 +/* + * Field masks and offsets for the SGM776_SDS_RESET_SYNDROME structure. + */ +#define SGM776_SDS_RESET_SYNDROME_POR_MASK 0x1 +#define SGM776_SDS_RESET_SYNDROME_WDOGSCP_MASK 0x2 +#define SGM776_SDS_RESET_SYNDROME_WDOGAP_MASK 0x4 +#define SGM776_SDS_RESET_SYNDROME_SYSRESET_MASK 0x8 +#define SGM776_SDS_RESET_SYNDROME_M3LOCKUP_MASK 0x10 + +#define SGM776_SDS_RESET_SYNDROME_POR_POS 0 +#define SGM776_SDS_RESET_SYNDROME_WDOGSCP_POS 1 +#define SGM776_SDS_RESET_SYNDROME_WDOGAP_POS 2 +#define SGM776_SDS_RESET_SYNDROME_SYSRESET_POS 3 +#define SGM776_SDS_RESET_SYNDROME_M3LOCKUP_POS 4 + +/* + * Field masks and offsets for the SGM776_SDS_FEATURE_AVAILABILITY structure. + */ +#define SGM776_SDS_FEATURE_FIRMWARE_MASK 0x1 +#define SGM776_SDS_FEATURE_DMC_MASK 0x2 +#define SGM776_SDS_FEATURE_MESSAGING_MASK 0x4 + +#define SGM776_SDS_FEATURE_FIRMWARE_POS 0 +#define SGM776_SDS_FEATURE_DMC_POS 1 +#define SGM776_SDS_FEATURE_MESSAGING_POS 2 + +/* + * Field masks and offsets for the SGM776_SDS_CPU_BOOTCTR structure. + */ +#define SGM776_SDS_CPU_BOOTCTR_CPU0_MASK 0xFF +#define SGM776_SDS_CPU_BOOTCTR_CPU1_MASK 0xFF00 +#define SGM776_SDS_CPU_BOOTCTR_CPU2_MASK 0xFF0000 +#define SGM776_SDS_CPU_BOOTCTR_CPU3_MASK 0xFF000000 +#define SGM776_SDS_CPU_BOOTCTR_CPU4_MASK 0xFF +#define SGM776_SDS_CPU_BOOTCTR_CPU5_MASK 0xFF00 +#define SGM776_SDS_CPU_BOOTCTR_CPU6_MASK 0xFF0000 +#define SGM776_SDS_CPU_BOOTCTR_CPU7_MASK 0xFF000000 + + +#define SGM776_SDS_CPU_BOOTCTR_CPU0_POS 0 +#define SGM776_SDS_CPU_BOOTCTR_CPU1_POS 8 +#define SGM776_SDS_CPU_BOOTCTR_CPU2_POS 16 +#define SGM776_SDS_CPU_BOOTCTR_CPU3_POS 24 +#define SGM776_SDS_CPU_BOOTCTR_CPU4_POS 0 +#define SGM776_SDS_CPU_BOOTCTR_CPU5_POS 8 +#define SGM776_SDS_CPU_BOOTCTR_CPU6_POS 16 +#define SGM776_SDS_CPU_BOOTCTR_CPU7_POS 24 + +/* + * Field masks and offsets for the SGM776_SDS_CPU_FLAGS structure. + */ +#define SGM776_SDS_CPU_FLAGS_CPU0_WFI_MASK 0x1 +#define SGM776_SDS_CPU_FLAGS_CPU1_WFI_MASK 0x100 +#define SGM776_SDS_CPU_FLAGS_CPU2_WFI_MASK 0x10000 +#define SGM776_SDS_CPU_FLAGS_CPU3_WFI_MASK 0x1000000 +#define SGM776_SDS_CPU_FLAGS_CPU4_WFI_MASK 0x1 +#define SGM776_SDS_CPU_FLAGS_CPU5_WFI_MASK 0x100 +#define SGM776_SDS_CPU_FLAGS_CPU6_WFI_MASK 0x10000 +#define SGM776_SDS_CPU_FLAGS_CPU7_WFI_MASK 0x1000000 + +#define SGM776_SDS_CPU_FLAGS_CPU0_WFI_POS 0 +#define SGM776_SDS_CPU_FLAGS_CPU1_WFI_POS 8 +#define SGM776_SDS_CPU_FLAGS_CPU2_WFI_POS 16 +#define SGM776_SDS_CPU_FLAGS_CPU3_WFI_POS 24 +#define SGM776_SDS_CPU_FLAGS_CPU4_WFI_POS 0 +#define SGM776_SDS_CPU_FLAGS_CPU5_WFI_POS 8 +#define SGM776_SDS_CPU_FLAGS_CPU6_WFI_POS 16 +#define SGM776_SDS_CPU_FLAGS_CPU7_WFI_POS 24 +/* + * Field masks and offsets for the SGM776_SDS_BOOTLOADER structure. + */ +#define SGM776_SDS_BOOTLOADER_VALID_MASK 0x1 +#define SGM776_SDS_BOOTLOADER_OFFSET_MASK 0xFFFFFFFF +#define SGM776_SDS_BOOTLOADER_SIZE_MASK 0xFFFFFFFF + +#define SGM776_SDS_BOOTLOADER_VALID_POS 0 +#define SGM776_SDS_BOOTLOADER_OFFSET_POS 0 +#define SGM776_SDS_BOOTLOADER_SIZE_POS 0 + +#endif /* SGM776_SDS_H */ diff --git a/product/sgm776/include/sgm776_sid.h b/product/sgm776/include/sgm776_sid.h new file mode 100644 index 00000000..bcbb4fe9 --- /dev/null +++ b/product/sgm776/include/sgm776_sid.h @@ -0,0 +1,16 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2018-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef SGM776_SID_H +#define SGM776_SID_H + +enum sgm776_sid_part { + SGM776_SID_PART_DUKE = 0x791, + SGM776_SID_PART_DAVIS = 0x792, +}; + +#endif /* SGM776_SID_H */ diff --git a/product/sgm776/include/software_mmap.h b/product/sgm776/include/software_mmap.h new file mode 100644 index 00000000..081a54a6 --- /dev/null +++ b/product/sgm776/include/software_mmap.h @@ -0,0 +1,128 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + * + * Description: + * Software defined memory map shared between SCP and AP cores. + */ + +#ifndef SOFTWARE_MMAP_H +#define SOFTWARE_MMAP_H + +#include <fwk_macros.h> +#include <system_mmap.h> + +/* + * The 4KiB AP/SCP Shared memory at the base of Trusted SRAM is used for several + * purposes. These are: the Shared Data Storage (SDS) Memory Region, the SCMI + * secure payload areas, and the context area for Application Processor + * firmware. + * + * Shared Data Storage (SDS) Memory Region: Used for structured storage of data + * that is shared between SCP Firmware and Application Processor firmware. The + * SDS Memory Region occupies the area between the context region base and + * the SCMI Secure Payload base. + * + * SCMI Secure Payload Areas: Storage for SCMI message contents in both the + * Agent->Platform and Platform->Agent directions. + * + * Application Processor Context Area: The usage of this area is defined by the + * firmware running on the Application Processors. The SCP Firmware must zero + * this memory before releasing any Application Processors. This area must + * always be located in the top 64 bytes of the 4KiB reserved region. + * + * +-----------------------+ 4096 + * | | + * 64B | AP Context Area | + * | | + * +-----------------------+ + * | | + * 256B | Unused | + * | | + * +-----------------------+ + * | | + * | SCMI Sec. Payload | + * 128B | Platform to Agent | + * | | + * +-----------------------+ + * | | + * 128B | SCMI Sec. Payload | + * | Agent to Platform | + * | | + * +-----------------------+ + * | | + * 3520B | SDS Memory Region | + * | | + * +-----------------------+ 0 + */ + +/* Secure shared memory at the base of Trusted SRAM */ +#define SHARED_SECURE_BASE (TRUSTED_RAM_BASE) +#define SHARED_SECURE_SIZE (4 * FWK_KIB) + +/* SDS Memory Region */ +#define SDS_MEM_BASE (SHARED_SECURE_BASE) +#define SDS_MEM_SIZE (3520) + +/* AP Context Area */ +#define AP_CONTEXT_BASE (SHARED_SECURE_BASE + SHARED_SECURE_SIZE - \ + AP_CONTEXT_SIZE) +#define AP_CONTEXT_SIZE (64) + +/* SCMI Secure Payload Areas */ +#define SCMI_PAYLOAD_SIZE (128) +#define SCMI_PAYLOAD_S_A2P_BASE (SDS_MEM_BASE + SDS_MEM_SIZE) +#define SCMI_PAYLOAD_S_P2A_BASE (SCMI_PAYLOAD_S_A2P_BASE + SCMI_PAYLOAD_SIZE) + +/* + * The 4KiB AP/SCP Shared memory at the base of Non-trusted SRAM is used for the + * SCMI non-secure payload areas. + * + * Two SCMI non-Secure Payload Areas: Storage for SCMI message contents in both + * the Agent->Platform and Platform->Agent directions. + * + * +-----------------------+ 4096 + * 3584B | Unused | + * +-----------------------+ + * | | + * | Non-Sec. Channel 1 | + * | SCMI non-Sec. Payload | + * 128B | Platform to Agent | + * | | + * +-----------------------+ + * | | + * | Non-Sec. Channel 1 | + * 128B | SCMI non-Sec. Payload | + * | Agent to Platform | + * | | + * +-----------------------+ + * | | + * | Non-Sec. Channel 0 | + * | SCMI non-Sec. Payload | + * 128B | Platform to Agent | + * | | + * +-----------------------+ + * | | + * | Non-Sec. Channel 0 | + * 128B | SCMI non-Sec. Payload | + * | Agent to Platform | + * | | + * +-----------------------+ 0 + */ + +/* Non-secure shared memory at the base of Non-trusted SRAM */ +#define SHARED_NONSECURE_BASE (NONTRUSTED_RAM_BASE) +#define SHARED_NONSECURE_SIZE (4 * FWK_KIB) + +/* SCMI Non-Secure Payload Areas */ +#define SCMI_PAYLOAD0_NS_A2P_BASE (SHARED_NONSECURE_BASE) +#define SCMI_PAYLOAD0_NS_P2A_BASE (SCMI_PAYLOAD0_NS_A2P_BASE + \ + SCMI_PAYLOAD_SIZE) +#define SCMI_PAYLOAD1_NS_A2P_BASE (SCMI_PAYLOAD0_NS_P2A_BASE + \ + SCMI_PAYLOAD_SIZE) +#define SCMI_PAYLOAD1_NS_P2A_BASE (SCMI_PAYLOAD1_NS_A2P_BASE + \ + SCMI_PAYLOAD_SIZE) + +#endif /* SOFTWARE_MMAP_H */ diff --git a/product/sgm776/include/system_clock.h b/product/sgm776/include/system_clock.h new file mode 100644 index 00000000..923e3d34 --- /dev/null +++ b/product/sgm776/include/system_clock.h @@ -0,0 +1,16 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef SYSTEM_CLOCK_H +#define SYSTEM_CLOCK_H + +#include <fwk_macros.h> + +#define CLOCK_RATE_REFCLK (50UL * FWK_MHZ) +#define CLOCK_RATE_SYSPLLCLK (3600UL * FWK_MHZ) + +#endif /* SYSTEM_CLOCK_H */ diff --git a/product/sgm776/include/system_mmap.h b/product/sgm776/include/system_mmap.h new file mode 100644 index 00000000..92594402 --- /dev/null +++ b/product/sgm776/include/system_mmap.h @@ -0,0 +1,61 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef SYSTEM_MMAP_H +#define SYSTEM_MMAP_H + +#include <sgm776_mmap.h> + +#define DMC_EXTERNAL0 (SYS0_BASE + 0x3FBE0000) +#define DMC_EXTERNAL1 (SYS0_BASE + 0x3FBF0000) +#define DMC_EXTERNAL2 (SYS0_BASE + 0x3FC00000) +#define DMC_EXTERNAL3 (SYS0_BASE + 0x3FC10000) + +#define BOARD_UART1_BASE (SYS0_BASE + 0x3FF70000) +#define PLAT_BASE (SYS0_BASE + 0x3FFE0000) + +#define PLL_GPU (PLAT_BASE + 0x00000008) +#define PLL_SYSTEM (PLAT_BASE + 0x0000000C) +#define PLL_VIDEO (PLAT_BASE + 0x00000010) +#define PLL_DISPLAY (PLAT_BASE + 0x00000014) + +#define PIX0_CONTROL (PLAT_BASE + 0x00000018) +#define PIX1_CONTROL (PLAT_BASE + 0x0000001C) + +#define SWCLKTCK_CONTROL (PLAT_BASE + 0x00000020) +#define SENSOR_SOC_TEMP (PLAT_BASE + 0x00000080) +#define PLATFORM_ID (PLAT_BASE + 0x000000E0) + +#define PLL_CLUS0_0 (PLAT_BASE + 0x00000100) +#define PLL_CLUS0_1 (PLAT_BASE + 0x00000104) +#define PLL_CLUS0_2 (PLAT_BASE + 0x00000108) +#define PLL_CLUS0_3 (PLAT_BASE + 0x0000010C) +#define PLL_CLUS0_4 (PLAT_BASE + 0x00000110) +#define PLL_CLUS0_5 (PLAT_BASE + 0x00000114) +#define PLL_CLUS0_6 (PLAT_BASE + 0x00000118) +#define PLL_CLUS0_7 (PLAT_BASE + 0x0000011C) + +#define DDR_PHY0 (SYS0_BASE + 0x3FB60000) +#define DDR_PHY1 (SYS0_BASE + 0x3FB70000) +#define DDR_PHY2 (SYS0_BASE + 0x3FB80000) +#define DDR_PHY3 (SYS0_BASE + 0x3FB90000) + +#define GPV_CCI_GPU1 (SYS1_BASE + 0x2A004000) +#define GPV_CCI_GPU0 (SYS1_BASE + 0x2A005000) +#define GPV_CCI_LITTLE (SYS1_BASE + 0x2A006000) +#define GPV_CCI_BIG (SYS1_BASE + 0x2A007000) +#define GPV_VPU (SYS1_BASE + 0x2A243000) +#define GPV_DPU0 (SYS1_BASE + 0x2A244000) +#define GPV_DPU1 (SYS1_BASE + 0x2A245000) + +#define DMC_INTERNAL0 (SYS1_BASE + 0x2A500000) +#define DMC_INTERNAL1 (SYS1_BASE + 0x2A540000) +#define DMC_INTERNAL2 (SYS1_BASE + 0x2A580000) +#define DMC_INTERNAL3 (SYS1_BASE + 0x2A5C0000) + + +#endif /* SYSTEM_MMAP_H */ diff --git a/product/sgm776/include/system_mmap_scp.h b/product/sgm776/include/system_mmap_scp.h new file mode 100644 index 00000000..4cb4d053 --- /dev/null +++ b/product/sgm776/include/system_mmap_scp.h @@ -0,0 +1,21 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + * + * Description: + * SCP ROM and RAM memory sizes. These definitions are kept isolated without + * the UINT32_C() or UL decorators allowing them to be used in the linker + * script. + */ + +#ifndef SYSTEM_MMAP_SCP_H +#define SYSTEM_MMAP_SCP_H + +#include <sgm776_mmap_scp.h> + +#define SCP_ROM_SIZE (64 * 1024) +#define SCP_RAM_SIZE (128 * 1024) + +#endif /* SYSTEM_MMAP_SCP_H */ diff --git a/product/sgm776/module/sgm776_system/include/mod_sgm776_system.h b/product/sgm776/module/sgm776_system/include/mod_sgm776_system.h new file mode 100644 index 00000000..851a05ec --- /dev/null +++ b/product/sgm776/module/sgm776_system/include/mod_sgm776_system.h @@ -0,0 +1,44 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + * + * Description: + * SGM776 System Support + */ + +#ifndef MOD_SGM776_SYSTEM_H +#define MOD_SGM776_SYSTEM_H + +/*! + * \addtogroup GroupSGM776Module SGM776 Product Modules + * @{ + */ + +/*! + * \defgroup GroupSGM776System SGM776 System Support + * + * @{ + */ + +/*! + * \brief API indices. + */ +enum mod_sgm776_system_api_idx { + /*! API index for the driver interface of the SYSTEM POWER module */ + MOD_SGM776_SYSTEM_API_IDX_SYSTEM_POWER_DRIVER, + + /*! Number of defined APIs */ + MOD_SGM776_SYSTEM_API_COUNT +}; + +/*! + * @} + */ + +/*! + * @} + */ + +#endif /* MOD_SGM776_SYSTEM_H */ diff --git a/product/sgm776/module/sgm776_system/src/Makefile b/product/sgm776/module/sgm776_system/src/Makefile new file mode 100644 index 00000000..b2408fcc --- /dev/null +++ b/product/sgm776/module/sgm776_system/src/Makefile @@ -0,0 +1,11 @@ +# +# Arm SCP/MCP Software +# Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. +# +# SPDX-License-Identifier: BSD-3-Clause +# + +BS_LIB_NAME := SGM776 SYSTEM +BS_LIB_SOURCES = mod_sgm776_system.c + +include $(BS_DIR)/lib.mk diff --git a/product/sgm776/module/sgm776_system/src/mod_sgm776_system.c b/product/sgm776/module/sgm776_system/src/mod_sgm776_system.c new file mode 100644 index 00000000..cfbba969 --- /dev/null +++ b/product/sgm776/module/sgm776_system/src/mod_sgm776_system.c @@ -0,0 +1,59 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + * + * Description: + * sgm776 System Support. + */ + +#include <fmw_cmsis.h> +#include <fwk_module.h> +#include <mod_system_power.h> +#include <mod_sgm776_system.h> + +/* + * Functions fulfilling the framework's module interface + */ + +static int sgm776_system_shutdown(enum mod_pd_system_shutdown system_shutdown) +{ + NVIC_SystemReset(); + + return FWK_E_DEVICE; +} + +static const struct mod_system_power_driver_api + sgm776_system_system_power_driver_api = { + .system_shutdown = sgm776_system_shutdown +}; + +/* + * Functions fulfilling the framework's module interface + */ + +static int sgm776_system_init(fwk_id_t module_id, unsigned int unused, + const void *unused2) +{ + return FWK_SUCCESS; +} + +static int sgm776_system_process_bind_request(fwk_id_t source_id, + fwk_id_t target_id, fwk_id_t api_id, const void **api) +{ + *api = &sgm776_system_system_power_driver_api; + + return FWK_SUCCESS; +} + +const struct fwk_module module_sgm776_system = { + .name = "sgm776_SYSTEM", + .api_count = MOD_SGM776_SYSTEM_API_COUNT, + .type = FWK_MODULE_TYPE_DRIVER, + .init = sgm776_system_init, + .process_bind_request = sgm776_system_process_bind_request, +}; + +/* No elements, no module configuration data */ +struct fwk_module_config config_sgm776_system = { 0 }; diff --git a/product/sgm776/product.mk b/product/sgm776/product.mk new file mode 100644 index 00000000..9333cd50 --- /dev/null +++ b/product/sgm776/product.mk @@ -0,0 +1,14 @@ +# +# Arm SCP/MCP Software +# Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. +# +# SPDX-License-Identifier: BSD-3-Clause +# +# Platforms supported by the sgm776 product: Duke. +# + +BS_PRODUCT_NAME := sgm776 + +BS_FIRMWARE_LIST := \ + scp_romfw \ + scp_ramfw diff --git a/product/sgm776/scp_ramfw/RTX_Config.h b/product/sgm776/scp_ramfw/RTX_Config.h new file mode 100644 index 00000000..eaa90d80 --- /dev/null +++ b/product/sgm776/scp_ramfw/RTX_Config.h @@ -0,0 +1,56 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + * + * Description: + * RTX2 v5 configuration file. + * The file must be called RTX_Config.h as it is included by an RTX file + * in order to create an object file containing the configuration. + */ + +#ifndef RTX_CONFIG_H_ +#define RTX_CONFIG_H_ + +/* System */ +#define OS_DYNAMIC_MEM_SIZE 0 +#define OS_TICK_FREQ 1000 /* Hz */ +#define OS_ROBIN_ENABLE 0 +#define OS_ROBIN_TIMEOUT 0 +#define OS_ISR_FIFO_QUEUE 16 + +/* Thread */ +#define OS_THREAD_OBJ_MEM 0 +#define OS_THREAD_NUM 1 +#define OS_THREAD_DEF_STACK_NUM 0 +#define OS_THREAD_USER_STACK_SIZE 0 +#define OS_STACK_SIZE 200 +#define OS_IDLE_THREAD_STACK_SIZE 200 +#define OS_STACK_CHECK 1 +#define OS_STACK_WATERMARK 0 +#define OS_PRIVILEGE_MODE 1 + +/* Timer */ +#define OS_TIMER_OBJ_MEM 0 +#define OS_TIMER_NUM 1 +#define OS_TIMER_THREAD_PRIO 40 +#define OS_TIMER_THREAD_STACK_SIZE 200 +#define OS_TIMER_CB_QUEUE 4 + +/* Event flags */ +#define OS_EVFLAGS_OBJ_MEM 0 +#define OS_EVFLAGS_NUM 1 + +#define OS_MUTEX_OBJ_MEM 0 +#define OS_MUTEX_NUM 1 +#define OS_SEMAPHORE_OBJ_MEM 0 +#define OS_SEMAPHORE_NUM 1 +#define OS_MEMPOOL_OBJ_MEM 0 +#define OS_MEMPOOL_NUM 1 +#define OS_MEMPOOL_DATA_SIZE 0 +#define OS_MSGQUEUE_OBJ_MEM 0 +#define OS_MSGQUEUE_NUM 1 +#define OS_MSGQUEUE_DATA_SIZE 0 + +#endif /* RTX_CONFIG_H_ */ diff --git a/product/sgm776/scp_ramfw/clock_devices.h b/product/sgm776/scp_ramfw/clock_devices.h new file mode 100644 index 00000000..495c8c6f --- /dev/null +++ b/product/sgm776/scp_ramfw/clock_devices.h @@ -0,0 +1,26 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef CLOCK_DEVICES_H +#define CLOCK_DEVICES_H + +/*! + * \brief Clock device indexes. + */ +enum clock_dev_idx { + CLOCK_DEV_IDX_BIG, + CLOCK_DEV_IDX_LITTLE, + CLOCK_DEV_IDX_GPU, + CLOCK_DEV_IDX_VPU, + CLOCK_DEV_IDX_DPU, + CLOCK_DEV_IDX_PIXEL_0, + CLOCK_DEV_IDX_PIXEL_1, + CLOCK_DEV_IDX_INTERCONNECT, + CLOCK_DEV_IDX_COUNT +}; + +#endif /* CLOCK_DEVICES_H */ diff --git a/product/sgm776/scp_ramfw/config_clock.c b/product/sgm776/scp_ramfw/config_clock.c new file mode 100644 index 00000000..2994ffd0 --- /dev/null +++ b/product/sgm776/scp_ramfw/config_clock.c @@ -0,0 +1,118 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_element.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_clock.h> +#include <mod_css_clock.h> +#include <mod_system_pll.h> +#include <mod_pik_clock.h> +#include <mod_power_domain.h> +#include <config_power_domain.h> +#include <clock_devices.h> +#include <sgm776_core.h> + +static const struct fwk_element clock_dev_desc_table[] = { + [CLOCK_DEV_IDX_BIG] = { + .name = "CPU_GROUP_BIG", + .data = &((struct mod_clock_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_CSS_CLOCK, 0), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_CSS_CLOCK, + MOD_CSS_CLOCK_API_TYPE_CLOCK), + }), + }, + [CLOCK_DEV_IDX_LITTLE] = { + .name = "CPU_GROUP_LITTLE", + .data = &((struct mod_clock_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_CSS_CLOCK, 1), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_CSS_CLOCK, + MOD_CSS_CLOCK_API_TYPE_CLOCK), + }), + }, + [CLOCK_DEV_IDX_GPU] = { + .name = "GPU", + .data = &((struct mod_clock_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_CSS_CLOCK, 2), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_CSS_CLOCK, + MOD_CSS_CLOCK_API_TYPE_CLOCK), + }), + }, + [CLOCK_DEV_IDX_VPU] = { + .name = "VPU", + .data = &((struct mod_clock_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_CSS_CLOCK, 3), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_CSS_CLOCK, + MOD_CSS_CLOCK_API_TYPE_CLOCK), + }), + }, + [CLOCK_DEV_IDX_DPU] = { + .name = "DPU", + .data = &((struct mod_clock_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_CSS_CLOCK, 4), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_CSS_CLOCK, + MOD_CSS_CLOCK_API_TYPE_CLOCK), + }), + }, + [CLOCK_DEV_IDX_PIXEL_0] = { + .name = "PIXEL_0", + .data = &((struct mod_clock_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_SYSTEM_PLL, 5), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_SYSTEM_PLL, + MOD_SYSTEM_PLL_API_TYPE_DEFAULT), + }), + }, + [CLOCK_DEV_IDX_PIXEL_1] = { + .name = "PIXEL_1", + .data = &((struct mod_clock_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_SYSTEM_PLL, 6), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_SYSTEM_PLL, + MOD_SYSTEM_PLL_API_TYPE_DEFAULT), + }), + }, + [CLOCK_DEV_IDX_INTERCONNECT] = { + .name = "INTERCONNECT", + .data = &((struct mod_clock_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 11), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PIK_CLOCK, + MOD_PIK_CLOCK_API_TYPE_CLOCK), + }), + }, + [CLOCK_DEV_IDX_COUNT] = { 0 }, /* Termination description. */ +}; + +static const struct fwk_element *clock_get_dev_desc_table(fwk_id_t module_id) +{ + unsigned int i; + unsigned int core_count; + struct mod_clock_dev_config *dev_config; + + core_count = sgm776_core_get_count(); + + /* Configure all clocks to respond to changes in SYSTOP power state */ + for (i = 0; i < CLOCK_DEV_IDX_COUNT; i++) { + dev_config = + (struct mod_clock_dev_config *)clock_dev_desc_table[i].data; + dev_config->pd_source_id = FWK_ID_ELEMENT( + FWK_MODULE_IDX_POWER_DOMAIN, + CONFIG_POWER_DOMAIN_SYSTOP_CHILD_COUNT + core_count); + } + + return clock_dev_desc_table; +} + +struct fwk_module_config config_clock = { + .get_element_table = clock_get_dev_desc_table, + .data = &((struct mod_clock_config) { + .pd_transition_notification_id = FWK_ID_NOTIFICATION_INIT( + FWK_MODULE_IDX_POWER_DOMAIN, + MOD_PD_NOTIFICATION_IDX_POWER_STATE_TRANSITION), + .pd_pre_transition_notification_id = FWK_ID_NOTIFICATION_INIT( + FWK_MODULE_IDX_POWER_DOMAIN, + MOD_PD_NOTIFICATION_IDX_POWER_STATE_PRE_TRANSITION), + }), +}; diff --git a/product/sgm776/scp_ramfw/config_css_clock.c b/product/sgm776/scp_ramfw/config_css_clock.c new file mode 100644 index 00000000..183d9334 --- /dev/null +++ b/product/sgm776/scp_ramfw/config_css_clock.c @@ -0,0 +1,354 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_assert.h> +#include <fwk_element.h> +#include <fwk_id.h> +#include <fwk_macros.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_css_clock.h> +#include <mod_system_pll.h> +#include <mod_pik_clock.h> +#include <mod_sid.h> +#include <sgm776_pik.h> + +static const struct mod_css_clock_rate rate_table_cpu_group_big[] = { + { + /* Super Underdrive */ + .rate = 1313 * FWK_MHZ, + .pll_rate = 1313 * FWK_MHZ, + .clock_source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_PLL1, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + .clock_mod_numerator = 1, + .clock_mod_denominator = 1, + }, + { + /* Underdrive */ + .rate = 1531 * FWK_MHZ, + .pll_rate = 1531 * FWK_MHZ, + .clock_source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_PLL1, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + .clock_mod_numerator = 1, + .clock_mod_denominator = 1, + }, + { + /* Nominal */ + .rate = 1750 * FWK_MHZ, + .pll_rate = 1750 * FWK_MHZ, + .clock_source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_PLL1, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + .clock_mod_numerator = 1, + .clock_mod_denominator = 1, + }, + { + /* Overdrive */ + .rate = 2100 * FWK_MHZ, + .pll_rate = 2100 * FWK_MHZ, + .clock_source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_PLL1, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + .clock_mod_numerator = 1, + .clock_mod_denominator = 1, + }, + { + /* Super Overdrive */ + .rate = 2700 * FWK_MHZ, + .pll_rate = 2700 * FWK_MHZ, + .clock_source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_PLL1, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + .clock_mod_numerator = 1, + .clock_mod_denominator = 1, + }, +}; + +static const struct mod_css_clock_rate rate_table_cpu_group_little[] = { + { + /* Super Underdrive */ + .rate = 665 * FWK_MHZ, + .pll_rate = 665 * FWK_MHZ, + .clock_source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_PLL0, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + .clock_mod_numerator = 1, + .clock_mod_denominator = 1, + }, + { + /* Underdrive */ + .rate = 998 * FWK_MHZ, + .pll_rate = 998 * FWK_MHZ, + .clock_source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_PLL0, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + .clock_mod_numerator = 1, + .clock_mod_denominator = 1, + }, + { + /* Nominal */ + .rate = 1330 * FWK_MHZ, + .pll_rate = 1330 * FWK_MHZ, + .clock_source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_PLL0, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + .clock_mod_numerator = 1, + .clock_mod_denominator = 1, + }, + { + /* Overdrive */ + .rate = 1463 * FWK_MHZ, + .pll_rate = 1463 * FWK_MHZ, + .clock_source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_PLL0, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + .clock_mod_numerator = 1, + .clock_mod_denominator = 1, + }, + { + /* Super Overdrive */ + .rate = 2200 * FWK_MHZ, + .pll_rate = 2200 * FWK_MHZ, + .clock_source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_PLL0, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + .clock_mod_numerator = 1, + .clock_mod_denominator = 1, + }, +}; + +static const struct mod_css_clock_rate rate_table_gpu[] = { + { + .rate = 450 * FWK_MHZ, + .pll_rate = 450 * FWK_MHZ, + .clock_source = MOD_PIK_CLOCK_MSCLOCK_SOURCE_PRIVPLLCLK, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + }, + { + .rate = 487500 * FWK_KHZ, + .pll_rate = 487500 * FWK_KHZ, + .clock_source = MOD_PIK_CLOCK_MSCLOCK_SOURCE_PRIVPLLCLK, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + }, + { + .rate = 525 * FWK_MHZ, + .pll_rate = 525 * FWK_MHZ, + .clock_source = MOD_PIK_CLOCK_MSCLOCK_SOURCE_PRIVPLLCLK, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + }, + { + .rate = 562500 * FWK_KHZ, + .pll_rate = 562500 * FWK_KHZ, + .clock_source = MOD_PIK_CLOCK_MSCLOCK_SOURCE_PRIVPLLCLK, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + }, + { + /* Nominal */ + .rate = 800 * FWK_MHZ, + .pll_rate = 800 * FWK_MHZ, + .clock_source = MOD_PIK_CLOCK_MSCLOCK_SOURCE_PRIVPLLCLK, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + }, +}; + +static const struct mod_css_clock_rate rate_table_vpu[] = { + { + /* Nominal */ + .rate = 650 * FWK_MHZ, + .pll_rate = 650 * FWK_MHZ, + .clock_source = MOD_PIK_CLOCK_MSCLOCK_SOURCE_PRIVPLLCLK, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + }, +}; + +static const fwk_id_t member_table_cpu_big_cfg_a[] = { + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 6), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 7), +}; + +static const fwk_id_t member_table_cpu_little_cfg_a[] = { + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 0), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 1), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 2), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 3), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 4), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 5), +}; + +static const fwk_id_t member_table_cpu_big_cfg_b[] = { + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 4), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 5), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 6), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 7), +}; + +static const fwk_id_t member_table_cpu_little_cfg_b[] = { + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 0), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 1), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 2), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 3), +}; + +static const fwk_id_t member_table_gpu[] = { + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 8), +}; + +static const fwk_id_t member_table_vpu[] = { + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 9), +}; + +static const fwk_id_t member_table_dpu[] = { + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 10), +}; + +static const struct fwk_element css_clock_element_table[] = { + { + .name = "CPU_GROUP_BIG", + .data = &((struct mod_css_clock_dev_config) { + .clock_type = MOD_CSS_CLOCK_TYPE_INDEXED, + .rate_table = rate_table_cpu_group_big, + .rate_count = FWK_ARRAY_SIZE(rate_table_cpu_group_big), + .clock_switching_source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_SYSREFCLK, + .pll_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_SYSTEM_PLL, 1), + .pll_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_SYSTEM_PLL, + MOD_SYSTEM_PLL_API_TYPE_DEFAULT), + .member_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PIK_CLOCK, + MOD_PIK_CLOCK_API_TYPE_CSS), + .initial_rate = 2700 * FWK_MHZ, + .modulation_supported = true, + }), + }, + { + .name = "CPU_GROUP_LITTLE", + .data = &((struct mod_css_clock_dev_config) { + .clock_type = MOD_CSS_CLOCK_TYPE_INDEXED, + .rate_table = rate_table_cpu_group_little, + .rate_count = FWK_ARRAY_SIZE(rate_table_cpu_group_little), + .clock_switching_source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_SYSREFCLK, + .pll_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_SYSTEM_PLL, 0), + .pll_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_SYSTEM_PLL, + MOD_SYSTEM_PLL_API_TYPE_DEFAULT), + .member_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PIK_CLOCK, + MOD_PIK_CLOCK_API_TYPE_CSS), + .initial_rate = 2200 * FWK_MHZ, + .modulation_supported = true, + }), + }, + { + .name = "GPU", + .data = &((struct mod_css_clock_dev_config) { + .clock_type = MOD_CSS_CLOCK_TYPE_INDEXED, + .rate_table = rate_table_gpu, + .rate_count = FWK_ARRAY_SIZE(rate_table_gpu), + .clock_switching_source = MOD_PIK_CLOCK_GPUCLK_SOURCE_SYSREFCLK, + .pll_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_SYSTEM_PLL, 2), + .pll_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_SYSTEM_PLL, + MOD_SYSTEM_PLL_API_TYPE_DEFAULT), + .member_table = member_table_gpu, + .member_count = FWK_ARRAY_SIZE(member_table_gpu), + .member_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PIK_CLOCK, + MOD_PIK_CLOCK_API_TYPE_CSS), + .initial_rate = 800 * FWK_MHZ, + .modulation_supported = false, + }), + }, + { + .name = "VPU", + .data = &((struct mod_css_clock_dev_config) { + .clock_type = MOD_CSS_CLOCK_TYPE_INDEXED, + .rate_table = rate_table_vpu, + .rate_count = FWK_ARRAY_SIZE(rate_table_vpu), + .clock_switching_source = MOD_PIK_CLOCK_VPUCLK_SOURCE_SYSREFCLK, + .pll_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_SYSTEM_PLL, 4), + .pll_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_SYSTEM_PLL, + MOD_SYSTEM_PLL_API_TYPE_DEFAULT), + .member_table = member_table_vpu, + .member_count = FWK_ARRAY_SIZE(member_table_vpu), + .member_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PIK_CLOCK, + MOD_PIK_CLOCK_API_TYPE_CSS), + .initial_rate = 650 * FWK_MHZ, + .modulation_supported = false, + }), + }, + { + .name = "DPU", + .data = &((struct mod_css_clock_dev_config) { + .clock_type = MOD_CSS_CLOCK_TYPE_NON_INDEXED, + .clock_default_source = MOD_PIK_CLOCK_ACLKDPU_SOURCE_DISPLAYPLLCLK, + .clock_switching_source = MOD_PIK_CLOCK_ACLKDPU_SOURCE_SYSREFCLK, + .pll_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_SYSTEM_PLL, 3), + .pll_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_SYSTEM_PLL, + MOD_SYSTEM_PLL_API_TYPE_DEFAULT), + .member_table = member_table_dpu, + .member_count = FWK_ARRAY_SIZE(member_table_dpu), + .member_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PIK_CLOCK, + MOD_PIK_CLOCK_API_TYPE_CSS), + .initial_rate = 600 * FWK_MHZ, + .modulation_supported = false, + }), + }, + { 0 }, /* Termination description. */ +}; + +static const struct fwk_element *css_clock_get_element_table + (fwk_id_t module_id) +{ + int status; + struct mod_css_clock_dev_config *config_big; + struct mod_css_clock_dev_config *config_little; + const struct mod_sid_info *system_info; + + status = mod_sid_get_system_info(&system_info); + fwk_assert(status == FWK_SUCCESS); + + config_big = + (struct mod_css_clock_dev_config *) css_clock_element_table[0].data; + config_little = + (struct mod_css_clock_dev_config *) css_clock_element_table[1].data; + + switch (system_info->config_number) { + case 1: + case 5: + case 7: + case 8: + config_big->member_table = member_table_cpu_big_cfg_a; + config_big->member_count = FWK_ARRAY_SIZE(member_table_cpu_big_cfg_a); + + config_little->member_table = member_table_cpu_little_cfg_a; + config_little->member_count = + FWK_ARRAY_SIZE(member_table_cpu_little_cfg_a); + break; + case 2: + case 3: + case 4: + case 6: + config_big->member_table = member_table_cpu_big_cfg_b; + config_big->member_count = + FWK_ARRAY_SIZE(member_table_cpu_big_cfg_b); + + config_little->member_table = member_table_cpu_little_cfg_b; + config_little->member_count = + FWK_ARRAY_SIZE(member_table_cpu_little_cfg_b); + break; + default: + return NULL; + } + + return css_clock_element_table; +} + +const struct fwk_module_config config_css_clock = { + .get_element_table = css_clock_get_element_table, +}; diff --git a/product/sgm776/scp_ramfw/config_ddr_phy500.c b/product/sgm776/scp_ramfw/config_ddr_phy500.c new file mode 100644 index 00000000..61ddcebb --- /dev/null +++ b/product/sgm776/scp_ramfw/config_ddr_phy500.c @@ -0,0 +1,63 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ +#include <fwk_element.h> +#include <fwk_module.h> +#include <mod_ddr_phy500.h> +#include <system_mmap.h> + +/* Default configuration values for DDR PHY500 devices. */ +static const struct mod_ddr_phy500_reg ddr_reg_val = { + .T_CTRL_DELAY = 0x00000000, + .READ_DELAY = 0x00000003, + .T_CTRL_UPD_MIN = 0x00000000, + .DELAY_SEL = 0x0000000A, + .CAPTURE_MASK = 0x0000001f, + .T_RDDATA_EN = 0x00001C00, + .T_RDLAT = 0x00000016, + .T_WRLAT = 0x01000000, + .DFI_WR_PREMBL = 0x00000002, + .DFI_LP_ACK = 0x00641300, +}; + +/* Table of DDR PHY500 element descriptions. */ +static struct fwk_element ddr_phy500_element_table[] = { + [0] = { .name = "DDR_PHY500-0", + .data = &((struct mod_ddr_phy500_element_config) { + .ddr = DDR_PHY0, + }), + }, + [1] = { .name = "DDR_PHY500-1", + .data = &((struct mod_ddr_phy500_element_config) { + .ddr = DDR_PHY1, + }), + }, + [2] = { .name = "DDR_PHY500-2", + .data = &((struct mod_ddr_phy500_element_config) { + .ddr = DDR_PHY2, + }), + }, + [3] = { .name = "DDR_PHY500-3", + .data = &((struct mod_ddr_phy500_element_config) { + .ddr = DDR_PHY3, + }), + }, + [4] = { 0 }, /* Termination description. */ +}; + +static const struct fwk_element *ddr_phy500_get_element_table( + fwk_id_t module_id) +{ + return ddr_phy500_element_table; +} + +/* Configuration of the DDR PHY500 module. */ +const struct fwk_module_config config_ddr_phy500 = { + .get_element_table = ddr_phy500_get_element_table, + .data = &((struct mod_ddr_phy500_module_config) { + .ddr_reg_val = &ddr_reg_val, + }), +}; diff --git a/product/sgm776/scp_ramfw/config_dmc500.c b/product/sgm776/scp_ramfw/config_dmc500.c new file mode 100644 index 00000000..97380a8f --- /dev/null +++ b/product/sgm776/scp_ramfw/config_dmc500.c @@ -0,0 +1,221 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_element.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_dmc500.h> +#include <system_mmap.h> + +#define COL_BITS 1 +#define BANK_BITS 0 +#define RANK_BITS 1 +#define BANK_GROUP 0 +#define ROW_BITS 5 +#define MEM_TYPE 3 +#define MEM_BURST 2 +#define DEVICE_WIDTH 2 +#define ADDR_SHUTTER 2 + +static const struct mod_dmc500_reg reg_val = { + .ADDRESS_CONTROL = ADDRESS_CONTROL_VAL(RANK_BITS, + BANK_BITS, + ROW_BITS, + COL_BITS), + .RANK_REMAP_CONTROL = 0x00000000, + .MEMORY_TYPE = MEMORY_TYPE_VAL(BANK_GROUP, + DEVICE_WIDTH, + MEM_TYPE), + .FORMAT_CONTROL = FORMAT_CONTROL_VAL(MEM_BURST), + .DECODE_CONTROL = 0x00000011, + .FEATURE_CONTROL = 0x00000000, + .ODT_WR_CONTROL_31_00 = 0x00000000, + .ODT_RD_CONTROL_31_00 = 0x00000000, + .ODT_TIMING = 0x10001000, + .T_REFI = 0x0000030b, + .T_RFC = 0x000340d0, + .T_RDPDEN = 0x0000002e, + .T_RCD = 0x0000001d, + .T_RAS = 0x80000044, + .T_RP = 0x0000221d, + .T_RRD = 0x00001010, + .T_ACT_WINDOW = 0x00000040, + .T_RTR = 0x000c0808, + .T_RTW = 0x001f1f1f, + .T_RTP = 0x0000000C, + .T_WR = 0x00000035, + .T_WTR = 0x00082929, + .T_WTW = 0x000b0808, + .T_XTMW = 0x00000020, + .T_CLOCK_CONTROL = 0x1119030d, + .T_EP = 0x0000000C, + .T_XP = 0x000c000c, + .T_ESR = 0x00000019, + .T_XSR = 0x00e100e1, + .ADDRESS_MAP = ADDRESS_MAP_VAL(ADDR_SHUTTER), + .SI0_SI_INTERRUPT_CONTROL = 0x00000000, + .SI0_PMU_REQ_CONTROL = 0x00000B1A, + .SI0_PMU_REQ_ATTRIBUTE_MASK_0 = 0xB0562AA1, + .SI0_PMU_REQ_ATTRIBUTE_MATCH_0 = 0xD0FB6716, + .SI0_PMU_REQ_ATTRIBUTE_MASK_1 = 0x7FC24C15, + .SI0_PMU_REQ_ATTRIBUTE_MATCH_1 = 0xF7A9B2AC, + .SI0_PMU_REQ_ATTRIBUTE_MASK_2 = 0xDD35FA69, + .SI0_PMU_REQ_ATTRIBUTE_MATCH_2 = 0x3555A8F5, + .SI0_PMU_REQ_ATTRIBUTE_MASK_3 = 0xDE382B10, + .SI0_PMU_REQ_ATTRIBUTE_MATCH_3 = 0x3484B32C, + .SI0_THRESHOLD_CONTROL = 0x00000000, + .SI1_SI_INTERRUPT_CONTROL = 0x00000000, + .SI1_PMU_REQ_CONTROL = 0x00000B1A, + .SI1_PMU_REQ_ATTRIBUTE_MASK_0 = 0xB0562AA1, + .SI1_PMU_REQ_ATTRIBUTE_MATCH_0 = 0xD0FB6716, + .SI1_PMU_REQ_ATTRIBUTE_MASK_1 = 0x7FC24C15, + .SI1_PMU_REQ_ATTRIBUTE_MATCH_1 = 0xF7A9B2AC, + .SI1_PMU_REQ_ATTRIBUTE_MASK_2 = 0xDD35FA69, + .SI1_PMU_REQ_ATTRIBUTE_MATCH_2 = 0x3555A8F5, + .SI1_PMU_REQ_ATTRIBUTE_MASK_3 = 0xDE382B10, + .SI1_PMU_REQ_ATTRIBUTE_MATCH_3 = 0x3484B32C, + .SI1_THRESHOLD_CONTROL = 0x00000000, + .QUEUE_THRESHOLD_CONTROL_31_00 = 0x00000000, + .QUEUE_THRESHOLD_CONTROL_63_32 = 0x99887700, + .DCB_INTERRUPT_CONTROL = 0x00000000, + .PMU_DCB_CONTROL = 0x00000800, + .PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MASK_0 = 0xFD98CF7D, + .PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MATCH_0 = 0x9F276EB5, + .PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MASK_1 = 0x40B1FC24, + .PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MATCH_1 = 0x04BBF4FA, + .PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MASK_2 = 0x8089B0AF, + .PMU_DATA_CONTROL_BLOCK_ATTRIBUTE_MATCH_2 = 0x7D26E0BE, + .PMU_TAG_ENTRIES_ATTRIBUTE_MASK = 0x000000CE, + .PMU_TAG_ENTRIES_ATTRIBUTE_MATCH = 0x00000056, + .QE_INTERRUPT_CONTROL = 0x00000000, + .RANK_TURNAROUND_CONTROL = 0x0F0F0F0F, + .HIT_TURNAROUND_CONTROL = 0x8290BF8F, + .QOS_CLASS_CONTROL = 0x00000D50, + .ESCALATION_CONTROL = 0x00000F03, + .QV_CONTROL_31_00 = 0xE6543210, + .QV_CONTROL_63_32 = 0xFEDCBA98, + .RT_CONTROL_31_00 = 0x00000000, + .RT_CONTROL_63_32 = 0x00008800, + .TIMEOUT_CONTROL = 0x00000001, + .WRITE_PRIORITY_CONTROL_31_00 = 0x00000000, + .WRITE_PRIORITY_CONTROL_63_32 = 0xEC840000, + .DIR_TURNAROUND_CONTROL = 0x05050F00, + .HIT_PREDICTION_CONTROL = 0x00020705, + .REFRESH_PRIORITY = 0x00000204, + .MC_UPDATE_CONTROL = 0x0000ff00, + .PHY_UPDATE_CONTROL = 0x15A3925F, + .PHY_MASTER_CONTROL = 0x6875AF9A, + .LOW_POWER_CONTROL = 0x000E0801, + .PMU_QE_CONTROL = 0x00000C0D, + .PMU_QE_MUX = 0x05670023, + .PMU_QOS_ENGINE_ATTRIBUTE_MASK_0 = 0x000000F1, + .PMU_QOS_ENGINE_ATTRIBUTE_MATCH_0 = 0x00000662, + .PMU_QOS_ENGINE_ATTRIBUTE_MASK_1 = 0x000000DD, + .PMU_QOS_ENGINE_ATTRIBUTE_MATCH_1 = 0x00000097, + .PMU_QOS_ENGINE_ATTRIBUTE_MASK_2 = 0x0000001A, + .PMU_QOS_ENGINE_ATTRIBUTE_MATCH_2 = 0x00000755, + .PMU_QUEUED_ENTRIES_ATTRIBUTE_MASK = 0xAD625ED5, + .PMU_QUEUED_ENTRIES_ATTRIBUTE_MATCH = 0x853C65BB, + .MI_INTERRUPT_CONTROL = 0x00000000, + .POWER_DOWN_CONTROL = 0x00000005, + .REFRESH_CONTROL = 0x00000000, + .PMU_MI_CONTROL = 0x00000100, + .PMU_MEMORY_IF_ATTRIBUTE_MASK_0 = 0x0032BB0E, + .PMU_MEMORY_IF_ATTRIBUTE_MATCH_0 = 0x0033F5AB, + .PMU_MEMORY_IF_ATTRIBUTE_MASK_1 = 0x00296B28, + .PMU_MEMORY_IF_ATTRIBUTE_MATCH_1 = 0x002C67BF, + .PMU_BANK_STATES_ATTRIBUTE_MASK = 0x00000005, + .PMU_BANK_STATES_ATTRIBUTE_MATCH = 0x00000019, + .PMU_RANK_STATES_ATTRIBUTE_MASK = 0x0000001B, + .PMU_RANK_STATES_ATTRIBUTE_MATCH = 0x00000020, + .CFG_INTERRUPT_CONTROL = 0x00000000, + .T_RDDATA_EN = 0x00000001, + .T_PHYRDLAT = 0x0000003f, + .T_PHYWRLAT = 0x010f170e, + .ERR_RAMECC_CTLR = 0x00000000, + .PHY_POWER_CONTROL = 0x0000012a, + .T_PHY_TRAIN = 0x00f8000a, + .PHYUPD_INIT = 0x00000000, + .REFRESH_ENABLE = 0x00000001, + .MI_STATE_CONTROL = 0, + .QUEUE_STATE_CONTROL = 0, + .SI0_SI_STATE_CONTROL = 0, + .SI1_SI_STATE_CONTROL = 0, +}; + +/* Table of DMC500 elements descriptions. */ +static const struct fwk_element dmc500_element_table[] = { + [0] = { .name = "DMC500-0", + .data = &((struct mod_dmc500_element_config) { + .dmc = DMC_INTERNAL0, + .ddr_phy_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_DDR_PHY500, 0), + }), + }, + [1] = { .name = "DMC500-1", + .data = &((struct mod_dmc500_element_config) { + .dmc = DMC_INTERNAL1, + .ddr_phy_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_DDR_PHY500, 1), + }), + }, + [2] = { .name = "DMC500-2", + .data = &((struct mod_dmc500_element_config) { + .dmc = DMC_INTERNAL2, + .ddr_phy_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_DDR_PHY500, 2), + }), + }, + [3] = { .name = "DMC500-3", + .data = &((struct mod_dmc500_element_config) { + .dmc = DMC_INTERNAL3, + .ddr_phy_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_DDR_PHY500, 3), + }), + }, + [4] = { 0 }, /* Termination description. */ +}; + +static const struct fwk_element *dmc500_get_element_table(fwk_id_t module_id) +{ + return dmc500_element_table; +} + +static void direct_ddr_cmd(struct mod_dmc500_reg *dmc) +{ + dmc->DIRECT_CMD_SETTINGS = 0x00C80000; + dmc->DIRECT_CMD = 0x00000000; + dmc->DIRECT_CLK_DISABLE = 0x00280003; + dmc->CLK_STATUS_OVERRIDE = 0x00000003; + dmc->DIRECT_CMD_SETTINGS = 0x01F40003; + dmc->DIRECT_CMD = 0x00800080; + dmc->RANK_STATUS_OVERRIDE = 0x30000003; + dmc->DIRECT_CMD_SETTINGS = 0x04b00003; + dmc->DIRECT_CMD = 0x00800FE0; + dmc->DIRECT_CMD_SETTINGS = 0x00500003; + dmc->DIRECT_CMD = 0x008011E0; + dmc->DIRECT_CMD_SETTINGS = 0x00140003; + dmc->DIRECT_CMD = 0x06d601c6; + dmc->DIRECT_CMD_SETTINGS = 0x01000003; + dmc->DIRECT_CMD = 0x00f60dc6; + dmc->DIRECT_CMD_SETTINGS = 0x00140003; + dmc->DIRECT_CMD = 0x31d603c6; + dmc->DIRECT_CMD_SETTINGS = 0x00140003; + dmc->DIRECT_CMD = 0x16f601c6; + dmc->DIRECT_CMD_SETTINGS = 0x00140003; + dmc->DIRECT_CMD = 0x2dd602c6; + dmc->DIRECT_CMD_SETTINGS = 0x02000003; + dmc->DIRECT_CMD = 0x00d60de6; +} + +/* Configuration of the DMC500 module. */ +const struct fwk_module_config config_dmc500 = { + .get_element_table = dmc500_get_element_table, + .data = &((struct mod_dmc500_module_config) { + .timer_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_TIMER, 0), + .ddr_phy_module_id = FWK_ID_MODULE_INIT(FWK_MODULE_IDX_DDR_PHY500), + .ddr_phy_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_DDR_PHY500, 0), + .reg_val = ®_val, + .direct_ddr_cmd = direct_ddr_cmd, + }), +}; diff --git a/product/sgm776/scp_ramfw/config_dvfs.c b/product/sgm776/scp_ramfw/config_dvfs.c new file mode 100644 index 00000000..e48d5aea --- /dev/null +++ b/product/sgm776/scp_ramfw/config_dvfs.c @@ -0,0 +1,128 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_element.h> +#include <fwk_macros.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <config_dvfs.h> +#include <mod_dvfs.h> + +static const struct mod_dvfs_domain_config cpu_group_little = { + .psu_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PSU, 0), + .clock_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_CLOCK, 1), + .latency = 1200, + .sustained_idx = 2, + .opps = (struct mod_dvfs_opp[]) { + { + .frequency = 665 * FWK_MHZ, + .voltage = 100, + }, + { + .frequency = 998 * FWK_MHZ, + .voltage = 200, + }, + { + .frequency = 1330 * FWK_MHZ, + .voltage = 300, + }, + { + .frequency = 1463 * FWK_MHZ, + .voltage = 400, + }, + { + .frequency = 2200 * FWK_MHZ, + .voltage = 500, + }, + { 0 } + } +}; + +static const struct mod_dvfs_domain_config cpu_group_big = { + .psu_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PSU, 1), + .clock_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_CLOCK, 0), + .latency = 1200, + .sustained_idx = 2, + .opps = (struct mod_dvfs_opp[]) { + { + .frequency = 1313 * FWK_MHZ, + .voltage = 100, + }, + { + .frequency = 1531 * FWK_MHZ, + .voltage = 200, + }, + { + .frequency = 1750 * FWK_MHZ, + .voltage = 300, + }, + { + .frequency = 2100 * FWK_MHZ, + .voltage = 400, + }, + { + .frequency = 2700 * FWK_MHZ, + .voltage = 500, + }, + { 0 } + } +}; + +static const struct mod_dvfs_domain_config gpu = { + .psu_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PSU, 2), + .clock_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_CLOCK, 2), + .latency = 1200, + .sustained_idx = 4, + .opps = (struct mod_dvfs_opp[]) { + { + .frequency = 450 * FWK_MHZ, + .voltage = 100, + }, + { + .frequency = 487500 * FWK_KHZ, + .voltage = 200, + }, + { + .frequency = 525 * FWK_MHZ, + .voltage = 300, + }, + { + .frequency = 562500 * FWK_KHZ, + .voltage = 400, + }, + { + .frequency = 800 * FWK_MHZ, + .voltage = 500, + }, + { 0 } + } +}; + +static const struct fwk_element element_table[] = { + [DVFS_ELEMENT_IDX_LITTLE] = { + .name = "CPU_GROUP_LITTLE", + .data = &cpu_group_little, + }, + [DVFS_ELEMENT_IDX_BIG] = { + .name = "CPU_GROUP_BIG", + .data = &cpu_group_big, + }, + [DVFS_ELEMENT_IDX_GPU] = { + .name = "GPU", + .data = &gpu, + }, + { 0 } +}; + +static const struct fwk_element *dvfs_get_element_table(fwk_id_t module_id) +{ + return element_table; +} + +const struct fwk_module_config config_dvfs = { + .get_element_table = dvfs_get_element_table, +}; diff --git a/product/sgm776/scp_ramfw/config_dvfs.h b/product/sgm776/scp_ramfw/config_dvfs.h new file mode 100644 index 00000000..f5ec5ee3 --- /dev/null +++ b/product/sgm776/scp_ramfw/config_dvfs.h @@ -0,0 +1,18 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef CONFIG_DVFS_H +#define CONFIG_DVFS_H + +enum dvfs_element_idx { + DVFS_ELEMENT_IDX_LITTLE, + DVFS_ELEMENT_IDX_BIG, + DVFS_ELEMENT_IDX_GPU, + DVFS_ELEMENT_IDX_COUNT +}; + +#endif /* CONFIG_DVFS_H */ diff --git a/product/sgm776/scp_ramfw/config_log.c b/product/sgm776/scp_ramfw/config_log.c new file mode 100644 index 00000000..c418ef46 --- /dev/null +++ b/product/sgm776/scp_ramfw/config_log.c @@ -0,0 +1,63 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_banner.h> +#include <fwk_macros.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_clock.h> +#include <mod_log.h> +#include <mod_pl011.h> +#include <system_mmap.h> +#include <clock_devices.h> + +/* + * PL011 module + */ +static const struct fwk_element pl011_element_table[] = { + [0] = { + .name = "board-uart1", + .data = &((struct mod_pl011_device_config) { + .reg_base = BOARD_UART1_BASE, + .baud_rate_bps = 115200, + .clock_rate_hz = 24 * FWK_MHZ, + .clock_id = FWK_ID_ELEMENT_INIT( + FWK_MODULE_IDX_CLOCK, + CLOCK_DEV_IDX_INTERCONNECT), + }), + }, + [1] = { 0 }, +}; + +static const struct fwk_element *get_pl011_table(fwk_id_t module_id) +{ + return pl011_element_table; +} + +const struct fwk_module_config config_pl011 = { + .get_element_table = get_pl011_table, +}; + +/* + * Log module + */ +static const struct mod_log_config log_data = { + .device_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PL011, 0), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PL011, 0), + .log_groups = MOD_LOG_GROUP_ERROR | + MOD_LOG_GROUP_INFO | + MOD_LOG_GROUP_WARNING | + MOD_LOG_GROUP_DEBUG, + .banner = FWK_BANNER_SCP + FWK_BANNER_RAM_FIRMWARE + BUILD_VERSION_DESCRIBE_STRING "\n", +}; + +const struct fwk_module_config config_log = { + .get_element_table = NULL, + .data = &log_data, +}; diff --git a/product/sgm776/scp_ramfw/config_mhu.c b/product/sgm776/scp_ramfw/config_mhu.c new file mode 100644 index 00000000..9ba401fe --- /dev/null +++ b/product/sgm776/scp_ramfw/config_mhu.c @@ -0,0 +1,57 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_element.h> +#include <fwk_id.h> +#include <fwk_module.h> +#include <mod_mhu2.h> +#include <sgm776_irq.h> +#include <sgm776_mhu.h> +#include <sgm776_mmap.h> + +static const struct fwk_element mhu_element_table[] = { + [SGM776_MHU_DEVICE_IDX_S] = { + .name = "MHU_S", + .sub_element_count = 1, + .data = &((struct mod_mhu2_channel_config) { + .irq = MHU_SECURE_IRQ, + .recv = MHU_RECV_S_BASE, + .send = MHU_SEND_S_BASE, + .channel = 0, + }) + }, + [SGM776_MHU_DEVICE_IDX_NS_H] = { + .name = "MHU_NS_HIGH", + .sub_element_count = 1, + .data = &((struct mod_mhu2_channel_config) { + .irq = MHU_HIGH_PRIO_IRQ, + .recv = MHU_RECV_NS_BASE, + .send = MHU_SEND_NS_BASE, + .channel = 0, + }) + }, + [SGM776_MHU_DEVICE_IDX_NS_L] = { + .name = "MHU_NS_LOW", + .sub_element_count = 1, + .data = &((struct mod_mhu2_channel_config) { + .irq = MHU_LOW_PRIO_IRQ, + .recv = MHU_RECV_NS_BASE, + .send = MHU_SEND_NS_BASE, + .channel = 1, + }) + }, + [SGM776_MHU_DEVICE_IDX_COUNT] = { 0 }, +}; + +static const struct fwk_element *mhu_get_element_table(fwk_id_t module_id) +{ + return mhu_element_table; +} + +struct fwk_module_config config_mhu2 = { + .get_element_table = mhu_get_element_table, +}; diff --git a/product/sgm776/scp_ramfw/config_mock_psu.c b/product/sgm776/scp_ramfw/config_mock_psu.c new file mode 100644 index 00000000..0bfc203e --- /dev/null +++ b/product/sgm776/scp_ramfw/config_mock_psu.c @@ -0,0 +1,75 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_element.h> +#include <fwk_module.h> +#include <mod_mock_psu.h> + +static const struct fwk_element element_table[] = { + { + .name = "CPU_GROUP_LITTLE", + .data = &(const struct mod_mock_psu_element_cfg) { + .async_alarm_id = FWK_ID_NONE_INIT, + .async_alarm_api_id = FWK_ID_NONE_INIT, + + .async_response_id = FWK_ID_NONE_INIT, + .async_response_api_id = FWK_ID_NONE_INIT, + + .default_enabled = true, + .default_voltage = 100, + }, + }, + { + .name = "CPU_GROUP_BIG", + .data = &(const struct mod_mock_psu_element_cfg) { + .async_alarm_id = FWK_ID_NONE_INIT, + .async_alarm_api_id = FWK_ID_NONE_INIT, + + .async_response_id = FWK_ID_NONE_INIT, + .async_response_api_id = FWK_ID_NONE_INIT, + + .default_enabled = true, + .default_voltage = 100, + }, + }, + { + .name = "GPU", + .data = &(const struct mod_mock_psu_element_cfg) { + .async_alarm_id = FWK_ID_NONE_INIT, + .async_alarm_api_id = FWK_ID_NONE_INIT, + + .async_response_id = FWK_ID_NONE_INIT, + .async_response_api_id = FWK_ID_NONE_INIT, + + .default_enabled = true, + .default_voltage = 100, + }, + }, + { + .name = "VPU", + .data = &(const struct mod_mock_psu_element_cfg) { + .async_alarm_id = FWK_ID_NONE_INIT, + .async_alarm_api_id = FWK_ID_NONE_INIT, + + .async_response_id = FWK_ID_NONE_INIT, + .async_response_api_id = FWK_ID_NONE_INIT, + + .default_enabled = true, + .default_voltage = 100, + }, + }, + { 0 } +}; + +static const struct fwk_element *get_element_table(fwk_id_t module_id) +{ + return element_table; +} + +const struct fwk_module_config config_mock_psu = { + .get_element_table = get_element_table, +}; diff --git a/product/sgm776/scp_ramfw/config_pik_clock.c b/product/sgm776/scp_ramfw/config_pik_clock.c new file mode 100644 index 00000000..d09b5f2c --- /dev/null +++ b/product/sgm776/scp_ramfw/config_pik_clock.c @@ -0,0 +1,305 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_assert.h> +#include <fwk_element.h> +#include <fwk_id.h> +#include <fwk_macros.h> +#include <fwk_module.h> +#include <mod_pik_clock.h> +#include <mod_sid.h> +#include <sgm776_pik.h> +#include <system_clock.h> + +/* + * Rate lookup tables + */ + +static struct mod_pik_clock_rate rate_table_cpu_a55[] = { + { + .rate = 2200 * FWK_MHZ, + .source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_PLL0, + .divider_reg = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .divider = 1, /* Rate adjusted via CPU PLL */ + }, +}; + +static struct mod_pik_clock_rate rate_table_cpu_a75[] = { + { + .rate = 2700 * FWK_MHZ, + .source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_PLL1, + .divider_reg = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .divider = 1, /* Rate adjusted via CPU PLL */ + }, +}; + +static struct mod_pik_clock_rate rate_table_gpu[] = { + { + .rate = 800 * FWK_MHZ, + .source = MOD_PIK_CLOCK_MSCLOCK_SOURCE_PRIVPLLCLK, + .divider_reg = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .divider = 1, /* Rate adjusted via GPU PLL */ + }, +}; + +static struct mod_pik_clock_rate rate_table_vpu[] = { + { + .rate = 650 * FWK_MHZ, + .source = MOD_PIK_CLOCK_VPUCLK_SOURCE_VIDEOPLLCLK, + .divider_reg = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .divider = 1, /* Rate adjusted via VPU PLL */ + }, +}; + +static struct mod_pik_clock_rate rate_table_dpu[] = { + { + .rate = 600 * FWK_MHZ, + .source = MOD_PIK_CLOCK_ACLKDPU_SOURCE_DISPLAYPLLCLK, + .divider_reg = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .divider = 1, /* Rate adjusted via display PLL */ + }, +}; + +static const struct mod_pik_clock_rate rate_table_sys_nocmemclk[] = { + { + .rate = 720 * FWK_MHZ, + .source = MOD_PIK_CLOCK_MSCLOCK_SOURCE_SYSPLLCLK, + .divider_reg = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_SYS, + .divider = CLOCK_RATE_SYSPLLCLK / (720 * FWK_MHZ), + }, +}; + +static const struct fwk_element pik_clock_element_table[] = { + /* + * Cluster 0 CPUS + */ + { + .name = "CLUS0_CPU0", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_CLUSTER, + .is_group_member = true, + .control_reg = &PIK_CLUS0->CORECLK[0].CTRL, + .divext_reg = &PIK_CLUS0->CORECLK[0].DIV, + .modulator_reg = &PIK_CLUS0->CORECLK[0].MOD, + .initial_rate = 2200 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "CLUS0_CPU1", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_CLUSTER, + .is_group_member = true, + .control_reg = &PIK_CLUS0->CORECLK[1].CTRL, + .divext_reg = &PIK_CLUS0->CORECLK[1].DIV, + .modulator_reg = &PIK_CLUS0->CORECLK[1].MOD, + .initial_rate = 2200 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "CLUS0_CPU2", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_CLUSTER, + .is_group_member = true, + .control_reg = &PIK_CLUS0->CORECLK[2].CTRL, + .divext_reg = &PIK_CLUS0->CORECLK[2].DIV, + .modulator_reg = &PIK_CLUS0->CORECLK[2].MOD, + .initial_rate = 2200 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "CLUS0_CPU3", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_CLUSTER, + .is_group_member = true, + .control_reg = &PIK_CLUS0->CORECLK[3].CTRL, + .divext_reg = &PIK_CLUS0->CORECLK[3].DIV, + .modulator_reg = &PIK_CLUS0->CORECLK[3].MOD, + .initial_rate = 2200 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "CLUS0_CPU4", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_CLUSTER, + .is_group_member = true, + .control_reg = &PIK_CLUS0->CORECLK[4].CTRL, + .divext_reg = &PIK_CLUS0->CORECLK[4].DIV, + .modulator_reg = &PIK_CLUS0->CORECLK[4].MOD, + .initial_rate = 2700 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "CLUS0_CPU5", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_CLUSTER, + .is_group_member = true, + .control_reg = &PIK_CLUS0->CORECLK[5].CTRL, + .divext_reg = &PIK_CLUS0->CORECLK[5].DIV, + .modulator_reg = &PIK_CLUS0->CORECLK[5].MOD, + .initial_rate = 2700 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "CLUS0_CPU6", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_CLUSTER, + .is_group_member = true, + .control_reg = &PIK_CLUS0->CORECLK[6].CTRL, + .divext_reg = &PIK_CLUS0->CORECLK[6].DIV, + .modulator_reg = &PIK_CLUS0->CORECLK[6].MOD, + .initial_rate = 2700 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "CLUS0_CPU7", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_CLUSTER, + .is_group_member = true, + .control_reg = &PIK_CLUS0->CORECLK[7].CTRL, + .divext_reg = &PIK_CLUS0->CORECLK[7].DIV, + .modulator_reg = &PIK_CLUS0->CORECLK[7].MOD, + .initial_rate = 2700 * FWK_MHZ, + .defer_initialization = true, + }), + }, + /* + * GPU + */ + { + .name = "GPU", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_MULTI_SOURCE, + .is_group_member = true, + .control_reg = &PIK_GPU->GPUCLK_CTRL, + .divsys_reg = &PIK_GPU->GPUCLK_DIV1, + .divext_reg = &PIK_GPU->GPUCLK_DIV2, + .rate_table = rate_table_gpu, + .rate_count = FWK_ARRAY_SIZE(rate_table_gpu), + .initial_rate = 800 * FWK_MHZ, + .defer_initialization = true, + }), + }, + /* + * VPU + */ + { + .name = "VPU", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_MULTI_SOURCE, + .is_group_member = true, + .control_reg = &PIK_VPU->VIDEOCLK_CTRL, + .divsys_reg = &PIK_VPU->VIDEOCLK_DIV1, + .divext_reg = &PIK_VPU->VIDEOCLK_DIV2, + .rate_table = rate_table_vpu, + .rate_count = FWK_ARRAY_SIZE(rate_table_vpu), + .initial_rate = 650 * FWK_MHZ, + .defer_initialization = true, + }), + }, + /* + * DPU + */ + { + .name = "DPU", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_MULTI_SOURCE, + .is_group_member = true, + .control_reg = &PIK_DPU->ACLKDP_CTRL, + .divsys_reg = &PIK_DPU->ACLKDP_DIV1, + .divext_reg = &PIK_DPU->ACLKDP_DIV2, + .rate_table = rate_table_dpu, + .rate_count = FWK_ARRAY_SIZE(rate_table_dpu), + .initial_rate = 600 * FWK_MHZ, + .defer_initialization = true, + }), + }, + /* + * Arachne NOC + */ + { + .name = "INTERCONNECT", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_MULTI_SOURCE, + .is_group_member = false, + .control_reg = &PIK_SYSTEM->NOCMEMCLK_CTRL, + .divsys_reg = &PIK_SYSTEM->NOCMEMCLK_DIV1, + .rate_table = rate_table_sys_nocmemclk, + .rate_count = FWK_ARRAY_SIZE(rate_table_sys_nocmemclk), + .initial_rate = 720 * FWK_MHZ, + .defer_initialization = false, + }), + }, + { 0 }, /* Termination description. */ +}; + +static const struct fwk_element *pik_clock_get_element_table + (fwk_id_t module_id) +{ + int status; + int element_idx; + struct mod_pik_clock_dev_config *config; + const struct mod_sid_info *system_info; + + status = mod_sid_get_system_info(&system_info); + fwk_assert(status == FWK_SUCCESS); + + switch (system_info->config_number) { + case 1: + case 5: + case 7: + case 8: + /* CPUs 0-5: Little */ + for (element_idx = 0; element_idx < 6; element_idx++) { + config = (struct mod_pik_clock_dev_config *) + pik_clock_element_table[element_idx].data; + config->rate_table = rate_table_cpu_a55; + config->rate_count = FWK_ARRAY_SIZE(rate_table_cpu_a55); + } + /* CPUs 6-7: Big */ + for (element_idx = 6; element_idx < 8; element_idx++) { + config = (struct mod_pik_clock_dev_config *) + pik_clock_element_table[element_idx].data; + config->rate_table = rate_table_cpu_a75; + config->rate_count = FWK_ARRAY_SIZE(rate_table_cpu_a75); + } + break; + case 2: + case 3: + case 4: + case 6: + /* CPUs 0-3: Little */ + for (element_idx = 0; element_idx < 4; element_idx++) { + config = (struct mod_pik_clock_dev_config *) + pik_clock_element_table[element_idx].data; + config->rate_table = rate_table_cpu_a55; + config->rate_count = FWK_ARRAY_SIZE(rate_table_cpu_a55); + } + /* CPUs 4-7: Big */ + for (element_idx = 4; element_idx < 8; element_idx++) { + config = (struct mod_pik_clock_dev_config *) + pik_clock_element_table[element_idx].data; + config->rate_table = rate_table_cpu_a75; + config->rate_count = FWK_ARRAY_SIZE(rate_table_cpu_a75); + } + break; + default: + return NULL; + } + + return pik_clock_element_table; +} + +const struct fwk_module_config config_pik_clock = { + .get_element_table = pik_clock_get_element_table, +}; diff --git a/product/sgm776/scp_ramfw/config_power_domain.c b/product/sgm776/scp_ramfw/config_power_domain.c new file mode 100644 index 00000000..79c73d30 --- /dev/null +++ b/product/sgm776/scp_ramfw/config_power_domain.c @@ -0,0 +1,250 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <stdint.h> +#include <string.h> +#include <fwk_element.h> +#include <fwk_macros.h> +#include <fwk_mm.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <config_power_domain.h> +#include <config_ppu_v1.h> +#include <mod_system_power.h> +#include <mod_ppu_v1.h> +#include <mod_power_domain.h> +#include <sgm776_core.h> + +static const char *core_pd_name_table[SGM776_CORE_PER_CLUSTER_MAX] = { + "CLUS0CORE0", "CLUS0CORE1", "CLUS0CORE2", "CLUS0CORE3", + "CLUS0CORE4", "CLUS0CORE5", "CLUS0CORE6", "CLUS0CORE7", +}; + +/* Mask of the allowed states for the systop power domain */ +static const uint32_t systop_allowed_state_mask_table[] = { + [0] = MOD_PD_STATE_OFF_MASK | MOD_PD_STATE_ON_MASK | + (1 << MOD_SYSTEM_POWER_POWER_STATE_SLEEP0) | + (1 << MOD_SYSTEM_POWER_POWER_STATE_SLEEP1) +}; + +/* + * Mask of the allowed states for the top level power domains + * (but the cluster power domains) depending on the system states. + */ +static const uint32_t toplevel_allowed_state_mask_table[] = { + [MOD_PD_STATE_OFF] = MOD_PD_STATE_OFF_MASK, + [MOD_PD_STATE_ON] = MOD_PD_STATE_OFF_MASK | MOD_PD_STATE_ON_MASK, + [MOD_SYSTEM_POWER_POWER_STATE_SLEEP0] = MOD_PD_STATE_OFF_MASK, + [MOD_SYSTEM_POWER_POWER_STATE_SLEEP1] = MOD_PD_STATE_OFF_MASK +}; + +/* + * Mask of the allowed states for the cluster power domain depending on the + * system states. + */ +static const uint32_t cluster_pd_allowed_state_mask_table[] = { + [MOD_PD_STATE_OFF] = MOD_PD_STATE_OFF_MASK, + [MOD_PD_STATE_ON] = MOD_PD_STATE_OFF_MASK | MOD_PD_STATE_ON_MASK | + MOD_PD_STATE_SLEEP_MASK, + [MOD_SYSTEM_POWER_POWER_STATE_SLEEP0] = MOD_PD_STATE_OFF_MASK, + [MOD_SYSTEM_POWER_POWER_STATE_SLEEP1] = MOD_PD_STATE_OFF_MASK +}; + +/* Mask of the allowed states for a core depending on the cluster states. */ +static const uint32_t core_pd_allowed_state_mask_table[] = { + [MOD_PD_STATE_OFF] = MOD_PD_STATE_OFF_MASK, + [MOD_PD_STATE_ON] = MOD_PD_STATE_OFF_MASK | MOD_PD_STATE_ON_MASK | + MOD_PD_STATE_SLEEP_MASK, + [MOD_PD_STATE_SLEEP] = MOD_PD_STATE_OFF_MASK | MOD_PD_STATE_SLEEP_MASK, +}; + +/* Power module specific configuration data (none) */ +static const struct mod_power_domain_config sgm776_power_domain_config = { 0 }; + +static struct fwk_element sgm776_power_domain_static_element_table[] = { + [CONFIG_POWER_DOMAIN_SYSTOP_CHILD_CLUSTER0] = { + .name = "CLUS0", + .data = &((struct mod_power_domain_element_config) { + .attributes.pd_type = MOD_PD_TYPE_CLUSTER, + .tree_pos = MOD_PD_TREE_POS( + MOD_PD_LEVEL_1, + 0, + 0, + CONFIG_POWER_DOMAIN_SYSTOP_CHILD_CLUSTER0, + 0), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PPU_V1, + MOD_PPU_V1_API_IDX_POWER_DOMAIN_DRIVER), + .allowed_state_mask_table = cluster_pd_allowed_state_mask_table, + .allowed_state_mask_table_size = + FWK_ARRAY_SIZE(cluster_pd_allowed_state_mask_table) + }), + }, + [CONFIG_POWER_DOMAIN_SYSTOP_CHILD_DBGTOP] = { + .name = "DBGTOP", + .data = &((struct mod_power_domain_element_config) { + .attributes.pd_type = MOD_PD_TYPE_DEVICE_DEBUG, + .tree_pos = MOD_PD_TREE_POS( + MOD_PD_LEVEL_1, + 0, + 0, + CONFIG_POWER_DOMAIN_SYSTOP_CHILD_DBGTOP, + 0), + .driver_id = FWK_ID_ELEMENT_INIT( + FWK_MODULE_IDX_PPU_V1, PPU_V1_ELEMENT_IDX_DBGTOP), + .api_id = FWK_ID_API_INIT( + FWK_MODULE_IDX_PPU_V1, + MOD_PPU_V1_API_IDX_POWER_DOMAIN_DRIVER), + .allowed_state_mask_table = toplevel_allowed_state_mask_table, + .allowed_state_mask_table_size = + FWK_ARRAY_SIZE(toplevel_allowed_state_mask_table) + }), + }, + [CONFIG_POWER_DOMAIN_SYSTOP_CHILD_DPUTOP] = { + .name = "DPUTOP", + .data = &((struct mod_power_domain_element_config) { + .attributes.pd_type = MOD_PD_TYPE_DEVICE, + .tree_pos = MOD_PD_TREE_POS( + MOD_PD_LEVEL_1, + 0, + 0, + CONFIG_POWER_DOMAIN_SYSTOP_CHILD_DPUTOP, + 0), + .driver_id = FWK_ID_ELEMENT_INIT( + FWK_MODULE_IDX_PPU_V1, PPU_V1_ELEMENT_IDX_DPUTOP), + .api_id = FWK_ID_API_INIT( + FWK_MODULE_IDX_PPU_V1, + MOD_PPU_V1_API_IDX_POWER_DOMAIN_DRIVER), + .allowed_state_mask_table = toplevel_allowed_state_mask_table, + .allowed_state_mask_table_size = + FWK_ARRAY_SIZE(toplevel_allowed_state_mask_table) + }), + }, + [CONFIG_POWER_DOMAIN_SYSTOP_CHILD_GPUTOP] = { + .name = "GPUTOP", + .data = &((struct mod_power_domain_element_config) { + .attributes.pd_type = MOD_PD_TYPE_DEVICE, + .tree_pos = MOD_PD_TREE_POS( + MOD_PD_LEVEL_1, + 0, + 0, + CONFIG_POWER_DOMAIN_SYSTOP_CHILD_GPUTOP, + 0), + .driver_id = FWK_ID_ELEMENT_INIT( + FWK_MODULE_IDX_PPU_V1, PPU_V1_ELEMENT_IDX_GPUTOP), + .api_id = FWK_ID_API_INIT( + FWK_MODULE_IDX_PPU_V1, + MOD_PPU_V1_API_IDX_POWER_DOMAIN_DRIVER), + .allowed_state_mask_table = toplevel_allowed_state_mask_table, + .allowed_state_mask_table_size = + FWK_ARRAY_SIZE(toplevel_allowed_state_mask_table) + }), + }, + [CONFIG_POWER_DOMAIN_SYSTOP_CHILD_VPUTOP] = { + .name = "VPUTOP", + .data = &((struct mod_power_domain_element_config) { + .attributes.pd_type = MOD_PD_TYPE_DEVICE, + .tree_pos = MOD_PD_TREE_POS( + MOD_PD_LEVEL_1, + 0, + 0, + CONFIG_POWER_DOMAIN_SYSTOP_CHILD_VPUTOP, + 0), + .driver_id = FWK_ID_ELEMENT_INIT( + FWK_MODULE_IDX_PPU_V1, PPU_V1_ELEMENT_IDX_VPUTOP), + .api_id = FWK_ID_API_INIT( + FWK_MODULE_IDX_PPU_V1, + MOD_PPU_V1_API_IDX_POWER_DOMAIN_DRIVER), + .allowed_state_mask_table = toplevel_allowed_state_mask_table, + .allowed_state_mask_table_size = + FWK_ARRAY_SIZE(toplevel_allowed_state_mask_table) + }), + }, + [CONFIG_POWER_DOMAIN_SYSTOP_CHILD_COUNT] = { + .name = "SYSTOP", + .data = &((struct mod_power_domain_element_config) { + .attributes.pd_type = MOD_PD_TYPE_SYSTEM, + .tree_pos = MOD_PD_TREE_POS( + MOD_PD_LEVEL_2, 0, 0, 0, 0), + .driver_id = FWK_ID_MODULE_INIT(FWK_MODULE_IDX_SYSTEM_POWER), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_SYSTEM_POWER, + MOD_SYSTEM_POWER_API_IDX_PD_DRIVER), + .allowed_state_mask_table = systop_allowed_state_mask_table, + .allowed_state_mask_table_size = + FWK_ARRAY_SIZE(systop_allowed_state_mask_table) + }), + }, +}; + + +/* + * Function definitions with internal linkage + */ +static const struct fwk_element *sgm776_power_domain_get_element_table + (fwk_id_t module_id) +{ + struct fwk_element *element_table, *element; + struct mod_power_domain_element_config *pd_config_table, *pd_config; + unsigned int core_idx; + + element_table = fwk_mm_calloc( + sgm776_core_get_count() + + FWK_ARRAY_SIZE(sgm776_power_domain_static_element_table) + + 1, /* Terminator */ + sizeof(struct fwk_element)); + if (element_table == NULL) + return NULL; + + pd_config_table = fwk_mm_calloc(sgm776_core_get_count(), + sizeof(struct mod_power_domain_element_config)); + if (pd_config_table == NULL) + return NULL; + + for (core_idx = 0; core_idx < sgm776_core_get_count(); core_idx++) { + element = &element_table[core_idx]; + pd_config = &pd_config_table[core_idx]; + + element->name = core_pd_name_table[core_idx]; + element->data = pd_config; + + pd_config->attributes.pd_type = MOD_PD_TYPE_CORE, + pd_config->tree_pos = MOD_PD_TREE_POS( + MOD_PD_LEVEL_0, + 0, + 0, + CONFIG_POWER_DOMAIN_SYSTOP_CHILD_CLUSTER0, + core_idx), + pd_config->driver_id = FWK_ID_ELEMENT( + FWK_MODULE_IDX_PPU_V1, PPU_V1_ELEMENT_IDX_COUNT + core_idx), + pd_config->api_id = FWK_ID_API( + FWK_MODULE_IDX_PPU_V1, MOD_PPU_V1_API_IDX_POWER_DOMAIN_DRIVER), + pd_config->allowed_state_mask_table = core_pd_allowed_state_mask_table, + pd_config->allowed_state_mask_table_size = + FWK_ARRAY_SIZE(core_pd_allowed_state_mask_table); + } + + pd_config = (struct mod_power_domain_element_config *) + sgm776_power_domain_static_element_table + [CONFIG_POWER_DOMAIN_SYSTOP_CHILD_CLUSTER0] + .data; + pd_config->driver_id = + FWK_ID_ELEMENT(FWK_MODULE_IDX_PPU_V1, + PPU_V1_ELEMENT_IDX_COUNT + sgm776_core_get_count()); + + memcpy(element_table + sgm776_core_get_count(), + sgm776_power_domain_static_element_table, + sizeof(sgm776_power_domain_static_element_table)); + + return element_table; +} + +/* + * Power module configuration data + */ +struct fwk_module_config config_power_domain = { + .get_element_table = sgm776_power_domain_get_element_table, + .data = &sgm776_power_domain_config, +}; diff --git a/product/sgm776/scp_ramfw/config_power_domain.h b/product/sgm776/scp_ramfw/config_power_domain.h new file mode 100644 index 00000000..a510220b --- /dev/null +++ b/product/sgm776/scp_ramfw/config_power_domain.h @@ -0,0 +1,20 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2018-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef CONFIG_POWER_DOMAIN_H +#define CONFIG_POWER_DOMAIN_H + +enum systop_child_index { + CONFIG_POWER_DOMAIN_SYSTOP_CHILD_CLUSTER0, + CONFIG_POWER_DOMAIN_SYSTOP_CHILD_DBGTOP, + CONFIG_POWER_DOMAIN_SYSTOP_CHILD_DPUTOP, + CONFIG_POWER_DOMAIN_SYSTOP_CHILD_GPUTOP, + CONFIG_POWER_DOMAIN_SYSTOP_CHILD_VPUTOP, + CONFIG_POWER_DOMAIN_SYSTOP_CHILD_COUNT +}; + +#endif /* CONFIG_POWER_DOMAIN_H */ diff --git a/product/sgm776/scp_ramfw/config_ppu_v1.c b/product/sgm776/scp_ramfw/config_ppu_v1.c new file mode 100644 index 00000000..57f3fe31 --- /dev/null +++ b/product/sgm776/scp_ramfw/config_ppu_v1.c @@ -0,0 +1,174 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <stddef.h> +#include <string.h> +#include <fwk_element.h> +#include <fwk_macros.h> +#include <fwk_mm.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_power_domain.h> +#include <mod_ppu_v1.h> +#include <sgm776_core.h> +#include <sgm776_irq.h> +#include <sgm776_mmap.h> +#include <config_power_domain.h> +#include <config_ppu_v1.h> + +static const char *core_pd_name_table[SGM776_CORE_PER_CLUSTER_MAX] = { + "CLUS0CORE0", "CLUS0CORE1", "CLUS0CORE2", "CLUS0CORE3", + "CLUS0CORE4", "CLUS0CORE5", "CLUS0CORE6", "CLUS0CORE7", +}; + +static uintptr_t core_pd_ppu_base_table[] = { + PPU_CLUS0CORE0_BASE, PPU_CLUS0CORE1_BASE, PPU_CLUS0CORE2_BASE, + PPU_CLUS0CORE3_BASE, PPU_CLUS0CORE4_BASE, PPU_CLUS0CORE5_BASE, + PPU_CLUS0CORE6_BASE, PPU_CLUS0CORE7_BASE +}; + +static unsigned int core_pd_ppu_irq_table[] = { + PPU_CLUS0CORE0_IRQ, PPU_CLUS0CORE1_IRQ, PPU_CLUS0CORE2_IRQ, + PPU_CLUS0CORE3_IRQ, PPU_CLUS0CORE4_IRQ, PPU_CLUS0CORE5_IRQ, + PPU_CLUS0CORE6_IRQ, PPU_CLUS0CORE7_IRQ +}; + +struct mod_ppu_v1_config sgm776_ppu_v1_notification_config = { + .pd_notification_id = FWK_ID_NOTIFICATION_INIT( + FWK_MODULE_IDX_POWER_DOMAIN, + MOD_PD_NOTIFICATION_IDX_POWER_STATE_TRANSITION), +}; + +static const struct fwk_element static_ppu_table[] = { + [PPU_V1_ELEMENT_IDX_DBGTOP] = { + .name = "DBGTOP", + .data = &((struct mod_ppu_v1_pd_config) { + .pd_type = MOD_PD_TYPE_DEVICE_DEBUG, + .ppu.reg_base = PPU_DEBUG_BASE, + .ppu.irq = PPU_DEBUG_IRQ, + .observer_id = FWK_ID_NONE_INIT, + }), + }, + [PPU_V1_ELEMENT_IDX_DPUTOP] = { + .name = "DPU0TOP", + .data = &((struct mod_ppu_v1_pd_config) { + .pd_type = MOD_PD_TYPE_DEVICE, + .ppu.reg_base = PPU_DPU_BASE, + .ppu.irq = PPU_DPU_IRQ, + .observer_id = FWK_ID_NONE_INIT, + .default_power_on = true, + }), + }, + [PPU_V1_ELEMENT_IDX_GPUTOP] = { + .name = "GPUTOP", + .data = &((struct mod_ppu_v1_pd_config) { + .pd_type = MOD_PD_TYPE_DEVICE, + .ppu.reg_base = PPU_GPU_BASE, + .ppu.irq = PPU_GPU_IRQ, + .observer_id = FWK_ID_NONE_INIT, + .default_power_on = true, + }), + }, + [PPU_V1_ELEMENT_IDX_VPUTOP] = { + .name = "VPUTOP", + .data = &((struct mod_ppu_v1_pd_config) { + .pd_type = MOD_PD_TYPE_DEVICE, + .ppu.reg_base = PPU_VPU_BASE, + .ppu.irq = PPU_VPU_IRQ, + .observer_id = FWK_ID_NONE_INIT, + .default_power_on = true, + }), + }, + [PPU_V1_ELEMENT_IDX_SYS0] = { + .name = "SYS0", + .data = &((struct mod_ppu_v1_pd_config) { + .pd_type = MOD_PD_TYPE_SYSTEM, + .ppu.reg_base = PPU_SYS0_BASE, + .ppu.irq = PPU_SYS0_IRQ, + .observer_id = FWK_ID_NONE_INIT, + }), + }, + [PPU_V1_ELEMENT_IDX_SYS1] = { + .name = "SYS1", + .data = &((struct mod_ppu_v1_pd_config) { + .pd_type = MOD_PD_TYPE_SYSTEM, + .ppu.reg_base = PPU_SYS1_BASE, + .ppu.irq = PPU_SYS1_IRQ, + .observer_id = FWK_ID_NONE_INIT, + }), + }, +}; + +static const struct fwk_element *sgm776_ppu_v1_get_element_table( + fwk_id_t module_id) +{ + struct fwk_element *element_table, *element; + struct mod_ppu_v1_pd_config *pd_config_table, *pd_config; + unsigned int core_idx, table_size; + + /* + * Allocate element descriptors based on: + * Size of static ppu table + * + Number of cores + * +1 cluster descriptor + * +1 terminator descriptor + */ + table_size = FWK_ARRAY_SIZE(static_ppu_table) + sgm776_core_get_count() + 2; + element_table = fwk_mm_calloc(table_size, sizeof(struct fwk_element)); + if (element_table == NULL) + return NULL; + + /* Table to hold configs for all cores and the cluster */ + pd_config_table = fwk_mm_calloc(sgm776_core_get_count() + 1, + sizeof(struct mod_ppu_v1_pd_config)); + if (pd_config_table == NULL) + return NULL; + + /* Cores */ + for (core_idx = 0; core_idx < sgm776_core_get_count(); core_idx++) { + element = &element_table[PPU_V1_ELEMENT_IDX_COUNT + core_idx]; + pd_config = &pd_config_table[core_idx]; + + element->name = core_pd_name_table[core_idx]; + element->data = pd_config; + + pd_config->pd_type = MOD_PD_TYPE_CORE; + pd_config->ppu.reg_base = core_pd_ppu_base_table[core_idx]; + pd_config->ppu.irq = core_pd_ppu_irq_table[core_idx]; + pd_config->cluster_id = FWK_ID_ELEMENT(FWK_MODULE_IDX_PPU_V1, + table_size - 2); + pd_config->observer_id = FWK_ID_NONE; + } + + element = &element_table[table_size - 2]; + pd_config = &pd_config_table[sgm776_core_get_count()]; + + element->name = "CLUS0"; + element->data = pd_config; + + pd_config->pd_type = MOD_PD_TYPE_CLUSTER; + pd_config->ppu.reg_base = PPU_CLUS0_BASE; + pd_config->ppu.irq = PPU_CLUS0_IRQ; + pd_config->observer_id = FWK_ID_NONE; + + /* Copy static table to the beginning of the dynamic table */ + memcpy(element_table, static_ppu_table, sizeof(static_ppu_table)); + + sgm776_ppu_v1_notification_config.pd_source_id = FWK_ID_ELEMENT( + FWK_MODULE_IDX_POWER_DOMAIN, + CONFIG_POWER_DOMAIN_SYSTOP_CHILD_COUNT + sgm776_core_get_count()); + + return element_table; +} + +/* + * Power module configuration data + */ +struct fwk_module_config config_ppu_v1 = { + .get_element_table = sgm776_ppu_v1_get_element_table, + .data = &sgm776_ppu_v1_notification_config, +}; diff --git a/product/sgm776/scp_ramfw/config_ppu_v1.h b/product/sgm776/scp_ramfw/config_ppu_v1.h new file mode 100644 index 00000000..2cf9c766 --- /dev/null +++ b/product/sgm776/scp_ramfw/config_ppu_v1.h @@ -0,0 +1,21 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef CONFIG_PPU_V1_H +#define CONFIG_PPU_V1_H + +enum ppu_v1_static_element_idx { + PPU_V1_ELEMENT_IDX_DBGTOP, + PPU_V1_ELEMENT_IDX_SYS0, + PPU_V1_ELEMENT_IDX_SYS1, + PPU_V1_ELEMENT_IDX_DPUTOP, + PPU_V1_ELEMENT_IDX_GPUTOP, + PPU_V1_ELEMENT_IDX_VPUTOP, + PPU_V1_ELEMENT_IDX_COUNT, +}; + +#endif /* CONFIG_PPU_V1_H */ diff --git a/product/sgm776/scp_ramfw/config_psu.c b/product/sgm776/scp_ramfw/config_psu.c new file mode 100644 index 00000000..e9ebbdc0 --- /dev/null +++ b/product/sgm776/scp_ramfw/config_psu.c @@ -0,0 +1,57 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_element.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_mock_psu.h> +#include <mod_psu.h> + +static const struct fwk_element element_table[] = { + { + .name = "CPU_GROUP_LITTLE", + .data = &(const struct mod_psu_element_cfg) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_MOCK_PSU, 0), + .driver_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_MOCK_PSU, + MOD_MOCK_PSU_API_IDX_DRIVER) + }, + }, + { + .name = "CPU_GROUP_BIG", + .data = &(const struct mod_psu_element_cfg) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_MOCK_PSU, 1), + .driver_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_MOCK_PSU, + MOD_MOCK_PSU_API_IDX_DRIVER) + }, + }, + { + .name = "GPU", + .data = &(const struct mod_psu_element_cfg) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_MOCK_PSU, 2), + .driver_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_MOCK_PSU, + MOD_MOCK_PSU_API_IDX_DRIVER) + }, + }, + { + .name = "VPU", + .data = &(const struct mod_psu_element_cfg) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_MOCK_PSU, 3), + .driver_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_MOCK_PSU, + MOD_MOCK_PSU_API_IDX_DRIVER) + }, + }, + { 0 } +}; + +static const struct fwk_element *psu_get_element_table(fwk_id_t module_id) +{ + return element_table; +} + +const struct fwk_module_config config_psu = { + .get_element_table = psu_get_element_table, +}; diff --git a/product/sgm776/scp_ramfw/config_scmi.c b/product/sgm776/scp_ramfw/config_scmi.c new file mode 100644 index 00000000..fc128fca --- /dev/null +++ b/product/sgm776/scp_ramfw/config_scmi.c @@ -0,0 +1,86 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_element.h> +#include <fwk_id.h> +#include <fwk_macros.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <sgm776_scmi.h> +#include <mod_scmi.h> +#include <internal/scmi.h> +#include <mod_smt.h> + +static const struct fwk_element service_table[] = { + [SGM776_SCMI_SERVICE_IDX_PSCI] = { + .name = "SERVICE0", + .data = &((struct mod_scmi_service_config) { + .transport_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_SMT, + SGM776_SCMI_SERVICE_IDX_PSCI), + .transport_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_SMT, + MOD_SMT_API_IDX_SCMI_TRANSPORT), + .transport_notification_init_id = + FWK_ID_NOTIFICATION_INIT(FWK_MODULE_IDX_SMT, + MOD_SMT_NOTIFICATION_IDX_INITIALIZED), + .scmi_agent_id = SCMI_AGENT_ID_PSCI, + }), + }, + [SGM776_SCMI_SERVICE_IDX_OSPM_0] = { + .name = "SERVICE1", + .data = &((struct mod_scmi_service_config) { + .transport_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_SMT, + SGM776_SCMI_SERVICE_IDX_OSPM_0), + .transport_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_SMT, + MOD_SMT_API_IDX_SCMI_TRANSPORT), + .transport_notification_init_id = + FWK_ID_NOTIFICATION_INIT(FWK_MODULE_IDX_SMT, + MOD_SMT_NOTIFICATION_IDX_INITIALIZED), + .scmi_agent_id = SCMI_AGENT_ID_OSPM, + }), + }, + [SGM776_SCMI_SERVICE_IDX_OSPM_1] = { + .name = "SERVICE2", + .data = &((struct mod_scmi_service_config) { + .transport_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_SMT, + SGM776_SCMI_SERVICE_IDX_OSPM_1), + .transport_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_SMT, + MOD_SMT_API_IDX_SCMI_TRANSPORT), + .transport_notification_init_id = + FWK_ID_NOTIFICATION_INIT(FWK_MODULE_IDX_SMT, + MOD_SMT_NOTIFICATION_IDX_INITIALIZED), + .scmi_agent_id = SCMI_AGENT_ID_OSPM, + }), + }, + [SGM776_SCMI_SERVICE_IDX_COUNT] = { 0 } +}; + +static const struct fwk_element *get_service_table(fwk_id_t module_id) +{ + return service_table; +} + +static const struct mod_scmi_agent agent_table[] = { + [SCMI_AGENT_ID_OSPM] = { + .type = SCMI_AGENT_TYPE_OSPM, + .name = "OSPM", + }, + [SCMI_AGENT_ID_PSCI] = { + .type = SCMI_AGENT_TYPE_PSCI, + .name = "PSCI", + }, +}; + +struct fwk_module_config config_scmi = { + .get_element_table = get_service_table, + .data = &((struct mod_scmi_config) { + .protocol_count_max = 9, + .agent_count = FWK_ARRAY_SIZE(agent_table) - 1, + .agent_table = agent_table, + .vendor_identifier = "arm", + .sub_vendor_identifier = "arm", + }), +}; diff --git a/product/sgm776/scp_ramfw/config_scmi_apcore.c b/product/sgm776/scp_ramfw/config_scmi_apcore.c new file mode 100644 index 00000000..cfdfe5a2 --- /dev/null +++ b/product/sgm776/scp_ramfw/config_scmi_apcore.c @@ -0,0 +1,31 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2018-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_element.h> +#include <fwk_macros.h> +#include <fwk_module.h> +#include <mod_scmi_apcore.h> +#include <sgm776_core.h> +#include <sgm776_pik.h> + +static const struct mod_scmi_apcore_reset_register_group + reset_reg_group_table[] = { + { + .base_register = + (uintptr_t)&PIK_CLUS0->STATIC_CONFIG[0].RVBARADDR_LW, + .register_count = SGM776_CORE_PER_CLUSTER_MAX, + }, + }; + +const struct fwk_module_config config_scmi_apcore = { + .data = &((struct mod_scmi_apcore_config){ + .reset_register_width = MOD_SCMI_APCORE_REG_WIDTH_64, + .reset_register_group_count = + FWK_ARRAY_SIZE(reset_reg_group_table), + .reset_register_group_table = &reset_reg_group_table[0], + }), +}; diff --git a/product/sgm776/scp_ramfw/config_scmi_clock.c b/product/sgm776/scp_ramfw/config_scmi_clock.c new file mode 100644 index 00000000..27368930 --- /dev/null +++ b/product/sgm776/scp_ramfw/config_scmi_clock.c @@ -0,0 +1,70 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <stdint.h> +#include <fwk_element.h> +#include <fwk_macros.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_scmi_clock.h> +#include <sgm776_scmi.h> +#include <clock_devices.h> + +static const struct mod_scmi_clock_device agent_device_table_ospm[] = { + { + /* VPU */ + .element_id = + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_CLOCK, CLOCK_DEV_IDX_VPU), + .permissions = MOD_SCMI_CLOCK_PERM_ATTRIBUTES | + MOD_SCMI_CLOCK_PERM_DESCRIBE_RATES | + MOD_SCMI_CLOCK_PERM_GET_RATE | + MOD_SCMI_CLOCK_PERM_SET_RATE, + }, + { + /* DPU */ + .element_id = + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_CLOCK, CLOCK_DEV_IDX_DPU), + .permissions = MOD_SCMI_CLOCK_PERM_ATTRIBUTES | + MOD_SCMI_CLOCK_PERM_DESCRIBE_RATES | + MOD_SCMI_CLOCK_PERM_GET_RATE | + MOD_SCMI_CLOCK_PERM_SET_RATE, + }, + { + /* PIXEL_0 */ + .element_id = + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_CLOCK, CLOCK_DEV_IDX_PIXEL_0), + .permissions = MOD_SCMI_CLOCK_PERM_ATTRIBUTES | + MOD_SCMI_CLOCK_PERM_DESCRIBE_RATES | + MOD_SCMI_CLOCK_PERM_GET_RATE | + MOD_SCMI_CLOCK_PERM_SET_RATE, + }, + { + /* PIXEL_1 */ + .element_id = + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_CLOCK, CLOCK_DEV_IDX_PIXEL_1), + .permissions = MOD_SCMI_CLOCK_PERM_ATTRIBUTES | + MOD_SCMI_CLOCK_PERM_DESCRIBE_RATES | + MOD_SCMI_CLOCK_PERM_GET_RATE | + MOD_SCMI_CLOCK_PERM_SET_RATE, + }, +}; + +static const struct mod_scmi_clock_agent agent_table[SCMI_AGENT_ID_COUNT] = { + [SCMI_AGENT_ID_PSCI] = { 0 /* No access */ }, + [SCMI_AGENT_ID_OSPM] = { + .device_table = agent_device_table_ospm, + .device_count = FWK_ARRAY_SIZE(agent_device_table_ospm), + }, +}; + +const struct fwk_module_config config_scmi_clock = { + .data = &((struct mod_scmi_clock_config) { + .max_pending_transactions = 0, + .agent_table = agent_table, + .agent_count = FWK_ARRAY_SIZE(agent_table), + }), +}; diff --git a/product/sgm776/scp_ramfw/config_scmi_perf.c b/product/sgm776/scp_ramfw/config_scmi_perf.c new file mode 100644 index 00000000..e1dd43dc --- /dev/null +++ b/product/sgm776/scp_ramfw/config_scmi_perf.c @@ -0,0 +1,43 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <stdint.h> +#include <fwk_element.h> +#include <fwk_module.h> +#include <config_dvfs.h> +#include <sgm776_scmi.h> +#include <mod_scmi_perf.h> + +static const struct mod_scmi_perf_domain_config domains[] = { + [DVFS_ELEMENT_IDX_LITTLE] = { + .permissions = &(const uint32_t[]) { + [SCMI_AGENT_ID_OSPM] = MOD_SCMI_PERF_PERMS_SET_LEVEL | + MOD_SCMI_PERF_PERMS_SET_LIMITS, + [SCMI_AGENT_ID_PSCI] = MOD_SCMI_PERF_PERMS_NONE, + } + }, + [DVFS_ELEMENT_IDX_BIG] = { + .permissions = &(const uint32_t[]) { + [SCMI_AGENT_ID_OSPM] = MOD_SCMI_PERF_PERMS_SET_LEVEL | + MOD_SCMI_PERF_PERMS_SET_LIMITS, + [SCMI_AGENT_ID_PSCI] = MOD_SCMI_PERF_PERMS_NONE, + } + }, + [DVFS_ELEMENT_IDX_GPU] = { + .permissions = &(const uint32_t[]) { + [SCMI_AGENT_ID_OSPM] = MOD_SCMI_PERF_PERMS_SET_LEVEL | + MOD_SCMI_PERF_PERMS_SET_LIMITS, + [SCMI_AGENT_ID_PSCI] = MOD_SCMI_PERF_PERMS_NONE, + } + }, +}; + +const struct fwk_module_config config_scmi_perf = { + .data = &((struct mod_scmi_perf_config) { + .domains = &domains, + }), +}; diff --git a/product/sgm776/scp_ramfw/config_scmi_system_power.c b/product/sgm776/scp_ramfw/config_scmi_system_power.c new file mode 100644 index 00000000..3302ccba --- /dev/null +++ b/product/sgm776/scp_ramfw/config_scmi_system_power.c @@ -0,0 +1,19 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <stddef.h> +#include <fwk_module.h> +#include <mod_scmi_system_power.h> +#include <mod_system_power.h> + +struct fwk_module_config config_scmi_system_power = { + .get_element_table = NULL, + .data = &((struct mod_scmi_system_power_config) { + .system_view = MOD_SCMI_SYSTEM_VIEW_FULL, + .system_suspend_state = MOD_SYSTEM_POWER_POWER_STATE_SLEEP0 + }), +}; diff --git a/product/sgm776/scp_ramfw/config_sds.c b/product/sgm776/scp_ramfw/config_sds.c new file mode 100644 index 00000000..95d68157 --- /dev/null +++ b/product/sgm776/scp_ramfw/config_sds.c @@ -0,0 +1,60 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <assert.h> +#include <stdint.h> +#include <fwk_element.h> +#include <fwk_macros.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_sds.h> +#include <sgm776_mmap.h> +#include <sgm776_sds.h> +#include <clock_devices.h> + +static const uint32_t feature_flags = SGM776_SDS_FEATURE_FIRMWARE_MASK; +static const uint32_t version_packed = FWK_BUILD_VERSION; + +const struct mod_sds_config sds_module_config = { + .region_base_address = TRUSTED_RAM_BASE, + .region_size = 3520, + .clock_id = FWK_ID_ELEMENT_INIT( + FWK_MODULE_IDX_CLOCK, + CLOCK_DEV_IDX_INTERCONNECT), +}; + +static const struct fwk_element sds_element_table[] = { + { + .name = "RAM Version", + .data = &((struct mod_sds_structure_desc) { + .id = SGM776_SDS_RAM_VERSION, + .size = SGM776_SDS_RAM_VERSION_SIZE, + .payload = &version_packed, + .finalize = true, + }), + }, + { + .name = "Feature Availability", + .data = &((struct mod_sds_structure_desc) { + .id = SGM776_SDS_FEATURE_AVAILABILITY, + .size = sizeof(feature_flags), + .payload = &feature_flags, + .finalize = true, + }), + }, + { 0 }, /* Termination description. */ +}; + +static const struct fwk_element *sds_get_element_table(fwk_id_t module_id) +{ + return sds_element_table; +} + +const struct fwk_module_config config_sds = { + .get_element_table = sds_get_element_table, + .data = &sds_module_config, +}; diff --git a/product/sgm776/scp_ramfw/config_sensor.c b/product/sgm776/scp_ramfw/config_sensor.c new file mode 100644 index 00000000..75c77a59 --- /dev/null +++ b/product/sgm776/scp_ramfw/config_sensor.c @@ -0,0 +1,75 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <stddef.h> +#include <fwk_element.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_reg_sensor.h> +#include <mod_sensor.h> +#include <system_mmap.h> + +enum REG_SENSOR_DEVICES { + REG_SENSOR_DEV_SOC_TEMP, + REG_SENSOR_DEV_COUNT, +}; + +/* + * Register Sensor driver config + */ + +static struct mod_sensor_info info_soc_temperature = { + .type = MOD_SENSOR_TYPE_DEGREES_C, + .update_interval = 0, + .update_interval_multiplier = 0, + .unit_multiplier = 0, +}; + +static const struct fwk_element reg_sensor_element_table[] = { + [REG_SENSOR_DEV_SOC_TEMP] = { + .name = "Soc Temperature", + .data = &((struct mod_reg_sensor_dev_config) { + .reg = (uintptr_t)(SENSOR_SOC_TEMP), + .info = &info_soc_temperature, + }), + }, + [REG_SENSOR_DEV_COUNT] = { 0 }, +}; + +static const struct fwk_element *get_reg_sensor_element_table(fwk_id_t id) +{ + return reg_sensor_element_table; +} + +struct fwk_module_config config_reg_sensor = { + .get_element_table = get_reg_sensor_element_table, +}; + +/* + * Sensor module config + */ +static const struct fwk_element sensor_element_table[] = { + [0] = { + .name = "Soc Temperature", + .data = &((const struct mod_sensor_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_REG_SENSOR, + REG_SENSOR_DEV_SOC_TEMP), + .driver_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_REG_SENSOR, 0), + }), + }, + [1] = { 0 }, +}; + +static const struct fwk_element *get_sensor_element_table(fwk_id_t module_id) +{ + return sensor_element_table; +} + +const struct fwk_module_config config_sensor = { + .get_element_table = get_sensor_element_table, + .data = NULL, +}; diff --git a/product/sgm776/scp_ramfw/config_smt.c b/product/sgm776/scp_ramfw/config_smt.c new file mode 100644 index 00000000..ee9fb7a4 --- /dev/null +++ b/product/sgm776/scp_ramfw/config_smt.c @@ -0,0 +1,82 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <stdint.h> +#include <fwk_element.h> +#include <fwk_id.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_clock.h> +#include <mod_mhu2.h> +#include <mod_smt.h> +#include <sgm776_core.h> +#include <sgm776_mhu.h> +#include <sgm776_scmi.h> +#include <config_power_domain.h> +#include <clock_devices.h> +#include <software_mmap.h> + +static const struct fwk_element smt_element_table[] = { + [SGM776_SCMI_SERVICE_IDX_PSCI] = { + .name = "PSCI", + .data = &((struct mod_smt_channel_config) { + .type = MOD_SMT_CHANNEL_TYPE_SLAVE, + .policies = MOD_SMT_POLICY_INIT_MAILBOX | MOD_SMT_POLICY_SECURE, + .mailbox_address = (uintptr_t)SCMI_PAYLOAD_S_A2P_BASE, + .mailbox_size = SCMI_PAYLOAD_SIZE, + .driver_id = FWK_ID_SUB_ELEMENT_INIT(FWK_MODULE_IDX_MHU2, + SGM776_MHU_DEVICE_IDX_S, 0), + .driver_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_MHU2, + MOD_MHU2_API_IDX_SMT_DRIVER), + }) + }, + [SGM776_SCMI_SERVICE_IDX_OSPM_0] = { + .name = "OSPM0", + .data = &((struct mod_smt_channel_config) { + .type = MOD_SMT_CHANNEL_TYPE_SLAVE, + .policies = MOD_SMT_POLICY_INIT_MAILBOX, + .mailbox_address = (uintptr_t)SCMI_PAYLOAD0_NS_A2P_BASE, + .mailbox_size = SCMI_PAYLOAD_SIZE, + .driver_id = FWK_ID_SUB_ELEMENT_INIT(FWK_MODULE_IDX_MHU2, + SGM776_MHU_DEVICE_IDX_NS_L, 0), + .driver_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_MHU2, + MOD_MHU2_API_IDX_SMT_DRIVER), + }) + }, + [SGM776_SCMI_SERVICE_IDX_OSPM_1] = { + .name = "OSPM1", + .data = &((struct mod_smt_channel_config) { + .type = MOD_SMT_CHANNEL_TYPE_SLAVE, + .policies = MOD_SMT_POLICY_INIT_MAILBOX, + .mailbox_address = (uintptr_t)SCMI_PAYLOAD1_NS_A2P_BASE, + .mailbox_size = SCMI_PAYLOAD_SIZE, + .driver_id = FWK_ID_SUB_ELEMENT_INIT(FWK_MODULE_IDX_MHU2, + SGM776_MHU_DEVICE_IDX_NS_H, 0), + .driver_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_MHU2, + MOD_MHU2_API_IDX_SMT_DRIVER), + }) + }, + [SGM776_SCMI_SERVICE_IDX_COUNT] = { 0 }, +}; + +static const struct fwk_element *smt_get_element_table(fwk_id_t module_id) +{ + unsigned int idx; + struct mod_smt_channel_config *config; + + for (idx = 0; idx < SGM776_SCMI_SERVICE_IDX_COUNT; idx++) { + config = (struct mod_smt_channel_config *)(smt_element_table[idx].data); + config->pd_source_id = FWK_ID_ELEMENT(FWK_MODULE_IDX_POWER_DOMAIN, + CONFIG_POWER_DOMAIN_SYSTOP_CHILD_COUNT + sgm776_core_get_count()); + } + + return smt_element_table; +} + +struct fwk_module_config config_smt = { + .get_element_table = smt_get_element_table, +}; diff --git a/product/sgm776/scp_ramfw/config_system_pll.c b/product/sgm776/scp_ramfw/config_system_pll.c new file mode 100644 index 00000000..829ed8f3 --- /dev/null +++ b/product/sgm776/scp_ramfw/config_system_pll.c @@ -0,0 +1,117 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_element.h> +#include <fwk_id.h> +#include <fwk_macros.h> +#include <fwk_module.h> +#include <mod_system_pll.h> +#include <sgm776_pik.h> +#include <system_mmap.h> + +static const struct fwk_element system_pll_element_table[] = { + { + .name = "CPU_PLL_0", + .data = &((struct mod_system_pll_dev_config) { + .control_reg = (void *)PLL_CLUS0_0, + .status_reg = (void *)&PIK_SCP->PLL_STATUS1, + .lock_flag_mask = PLL_STATUS1_CPUPLLLOCK(0, 0), + .initial_rate = 2200 * FWK_MHZ, + .min_rate = MOD_SYSTEM_PLL_MIN_RATE, + .max_rate = MOD_SYSTEM_PLL_MAX_RATE, + .min_step = MOD_SYSTEM_PLL_MIN_INTERVAL, + .defer_initialization = false, + }), + }, + { + .name = "CPU_PLL_1", + .data = &((struct mod_system_pll_dev_config) { + .control_reg = (void *)PLL_CLUS0_1, + .status_reg = (void *)&PIK_SCP->PLL_STATUS1, + .lock_flag_mask = PLL_STATUS1_CPUPLLLOCK(0, 1), + .initial_rate = 2700 * FWK_MHZ, + .min_rate = MOD_SYSTEM_PLL_MIN_RATE, + .max_rate = MOD_SYSTEM_PLL_MAX_RATE, + .min_step = MOD_SYSTEM_PLL_MIN_INTERVAL, + .defer_initialization = false, + }), + }, + { + .name = "GPU_PLL", + .data = &((struct mod_system_pll_dev_config) { + .control_reg = (void *)PLL_GPU, + .status_reg = (void *)&PIK_SCP->PLL_STATUS0, + .lock_flag_mask = PLL_STATUS0_GPUPLLLOCK, + .initial_rate = 800 * FWK_MHZ, + .min_rate = MOD_SYSTEM_PLL_MIN_RATE, + .max_rate = MOD_SYSTEM_PLL_MAX_RATE, + .min_step = MOD_SYSTEM_PLL_MIN_INTERVAL, + .defer_initialization = false, + }), + }, + { + .name = "DPU_PLL", + .data = &((struct mod_system_pll_dev_config) { + .control_reg = (void *)PLL_DISPLAY, + .status_reg = (void *)&PIK_SCP->PLL_STATUS0, + .lock_flag_mask = PLL_STATUS0_DISPLAYPLLLOCK, + .initial_rate = 600 * FWK_MHZ, + .min_rate = MOD_SYSTEM_PLL_MIN_RATE, + .max_rate = MOD_SYSTEM_PLL_MAX_RATE, + .min_step = MOD_SYSTEM_PLL_MIN_INTERVAL, + .defer_initialization = false, + }), + }, + { + .name = "VPU_PLL", + .data = &((struct mod_system_pll_dev_config) { + .control_reg = (void *)PLL_VIDEO, + .status_reg = (void *)&PIK_SCP->PLL_STATUS0, + .lock_flag_mask = PLL_STATUS0_VIDEOPLLLOCK, + .initial_rate = 650 * FWK_MHZ, + .min_rate = MOD_SYSTEM_PLL_MIN_RATE, + .max_rate = MOD_SYSTEM_PLL_MAX_RATE, + .min_step = MOD_SYSTEM_PLL_MIN_INTERVAL, + .defer_initialization = false, + }), + }, + { + .name = "PIX0_PLL", + .data = &((struct mod_system_pll_dev_config) { + .control_reg = (void *)PIX0_CONTROL, + .status_reg = NULL, + .initial_rate = 594 * FWK_MHZ, + .min_rate = 12500 * FWK_KHZ, + .max_rate = 594 * FWK_MHZ, + .min_step = 250 * FWK_KHZ, + .defer_initialization = false, + }), + }, + { + .name = "PIX1_PLL", + .data = &((struct mod_system_pll_dev_config) { + .control_reg = (void *)PIX1_CONTROL, + .status_reg = NULL, + .initial_rate = 594 * FWK_MHZ, + .min_rate = 12500 * FWK_KHZ, + .max_rate = 594 * FWK_MHZ, + .min_step = 250 * FWK_KHZ, + .defer_initialization = false, + }), + }, + { 0 }, /* Termination description. */ +}; + +static const struct fwk_element *system_pll_get_element_table + (fwk_id_t module_id) +{ + return system_pll_element_table; +} + +const struct fwk_module_config config_system_pll = { + .get_element_table = system_pll_get_element_table, +}; diff --git a/product/sgm776/scp_ramfw/config_system_power.c b/product/sgm776/scp_ramfw/config_system_power.c new file mode 100644 index 00000000..9edfbe3f --- /dev/null +++ b/product/sgm776/scp_ramfw/config_system_power.c @@ -0,0 +1,99 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_id.h> +#include <fwk_macros.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <sgm776_irq.h> +#include <config_ppu_v1.h> +#include <mod_ppu_v1.h> +#include <mod_system_power.h> +#include <mod_sgm776_system.h> + +/* + * The DPU/GPU/VPU PPUs in this list are there as a temporary workaround, until + * Linux supports handling these domains on its own. + */ +static const struct mod_system_power_ext_ppu_config ext_ppus[] = { + { + .ppu_id = FWK_ID_ELEMENT_INIT( + FWK_MODULE_IDX_PPU_V1, + PPU_V1_ELEMENT_IDX_DPUTOP), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PPU_V1, + MOD_PPU_V1_API_IDX_POWER_DOMAIN_DRIVER), + }, + { + .ppu_id = FWK_ID_ELEMENT_INIT( + FWK_MODULE_IDX_PPU_V1, + PPU_V1_ELEMENT_IDX_GPUTOP), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PPU_V1, + MOD_PPU_V1_API_IDX_POWER_DOMAIN_DRIVER), + }, + { + .ppu_id = FWK_ID_ELEMENT_INIT( + FWK_MODULE_IDX_PPU_V1, + PPU_V1_ELEMENT_IDX_VPUTOP), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PPU_V1, + MOD_PPU_V1_API_IDX_POWER_DOMAIN_DRIVER), + }, +}; + +static const uint8_t system_power_to_sys_ppu0_state[] = { + [MOD_PD_STATE_ON] = (uint8_t)MOD_PD_STATE_ON, + [MOD_SYSTEM_POWER_POWER_STATE_SLEEP0] = (uint8_t)MOD_PD_STATE_OFF, + [MOD_PD_STATE_OFF] = (uint8_t)MOD_PD_STATE_OFF, +}; + +static const uint8_t system_power_to_sys_ppu1_state[] = { + [MOD_PD_STATE_ON] = (uint8_t)MOD_PD_STATE_ON, + [MOD_SYSTEM_POWER_POWER_STATE_SLEEP0] = (uint8_t)MOD_PD_STATE_ON, + [MOD_PD_STATE_OFF] = (uint8_t)MOD_PD_STATE_OFF, +}; + +static const struct fwk_element system_power_element_table[] = { + [0] = { + .name = "SYS-PPU-0", + .data = &((struct mod_system_power_dev_config) { + .sys_ppu_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PPU_V1, + PPU_V1_ELEMENT_IDX_SYS0), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PPU_V1, 0), + .sys_state_table = system_power_to_sys_ppu0_state, + }), + }, + + [1] = { + .name = "SYS-PPU-1", + .data = &((struct mod_system_power_dev_config) { + .sys_ppu_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PPU_V1, + PPU_V1_ELEMENT_IDX_SYS1), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PPU_V1, 0), + .sys_state_table = system_power_to_sys_ppu1_state, + }), + }, + + [2] = { 0 }, /* Termination description */ +}; + +static const struct fwk_element *system_power_get_element_table( + fwk_id_t module_id) +{ + return system_power_element_table; +} + +const struct fwk_module_config config_system_power = { + .data = &((struct mod_system_power_config) { + .soc_wakeup_irq = SOC_WAKEUP0_IRQ, + .ext_ppus = ext_ppus, + .ext_ppus_count = FWK_ARRAY_SIZE(ext_ppus), + .driver_id = FWK_ID_MODULE_INIT(FWK_MODULE_IDX_SGM776_SYSTEM), + .driver_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_SGM776_SYSTEM, + MOD_SGM776_SYSTEM_API_IDX_SYSTEM_POWER_DRIVER), + .initial_system_power_state = MOD_PD_STATE_ON, + }), + .get_element_table = system_power_get_element_table, +}; diff --git a/product/sgm776/scp_ramfw/config_timer.c b/product/sgm776/scp_ramfw/config_timer.c new file mode 100644 index 00000000..69c5720e --- /dev/null +++ b/product/sgm776/scp_ramfw/config_timer.c @@ -0,0 +1,71 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_id.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_clock.h> +#include <mod_gtimer.h> +#include <mod_timer.h> +#include <sgm776_mmap.h> +#include <sgm776_irq.h> +#include <clock_devices.h> +#include <system_clock.h> + +/* + * Generic timer driver config + */ +static const struct fwk_element gtimer_dev_table[] = { + [0] = { + .name = "REFCLK", + .data = &((struct mod_gtimer_dev_config) { + .hw_timer = REFCLK_CNTBASE0_BASE, + .hw_counter = REFCLK_CNTCTL_BASE, + .control = REFCLK_CNTCONTROL_BASE, + .frequency = CLOCK_RATE_REFCLK, + .clock_id = FWK_ID_ELEMENT_INIT( + FWK_MODULE_IDX_CLOCK, + CLOCK_DEV_IDX_INTERCONNECT), + }) + }, + [1] = { 0 }, +}; + +static const struct fwk_element *gtimer_get_dev_table(fwk_id_t module_id) +{ + return gtimer_dev_table; +} + +const struct fwk_module_config config_gtimer = { + .get_element_table = gtimer_get_dev_table, +}; + +/* + * Timer HAL config + */ +static const struct mod_timer_dev_config refclk_config = { + .id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_GTIMER, 0), + .timer_irq = TIMREFCLK_IRQ, +}; + +static const struct fwk_element timer_dev_table[] = { + [0] = { + .name = "REFCLK", + .data = &refclk_config, + .sub_element_count = 8, /* Number of alarms */ + }, + [1] = { 0 }, +}; + +static const struct fwk_element *timer_get_dev_table(fwk_id_t module_id) +{ + return timer_dev_table; +} + +const struct fwk_module_config config_timer = { + .get_element_table = timer_get_dev_table, +}; diff --git a/product/sgm776/scp_ramfw/firmware.mk b/product/sgm776/scp_ramfw/firmware.mk new file mode 100644 index 00000000..26aca7bf --- /dev/null +++ b/product/sgm776/scp_ramfw/firmware.mk @@ -0,0 +1,73 @@ +# +# Arm SCP/MCP Software +# Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. +# +# SPDX-License-Identifier: BSD-3-Clause +# + +BS_FIRMWARE_CPU := cortex-m3 +BS_FIRMWARE_HAS_MULTITHREADING := yes +BS_FIRMWARE_HAS_NOTIFICATION := yes + +BS_FIRMWARE_MODULES := \ + sid \ + pcid \ + pl011 \ + log \ + gtimer \ + timer \ + ddr_phy500 \ + dmc500 \ + reg_sensor \ + sensor \ + ppu_v1 \ + system_power \ + sgm776_system \ + power_domain \ + psu \ + mock_psu \ + mhu2 \ + smt \ + system_pll \ + pik_clock \ + css_clock \ + clock \ + dvfs \ + scmi \ + scmi_power_domain \ + scmi_system_power \ + scmi_clock \ + scmi_perf \ + scmi_sensor \ + scmi_apcore \ + sds + +BS_FIRMWARE_SOURCES := \ + rtx_config.c \ + config_log.c \ + config_timer.c \ + config_ddr_phy500.c \ + config_dmc500.c \ + config_sensor.c \ + config_ppu_v1.c \ + config_system_power.c \ + config_power_domain.c \ + sgm776_core.c \ + config_sds.c \ + config_mhu.c \ + config_smt.c \ + config_scmi.c \ + config_scmi_system_power.c \ + config_scmi_clock.c \ + config_scmi_perf.c \ + config_scmi_apcore.c \ + config_system_pll.c \ + config_pik_clock.c \ + config_css_clock.c \ + config_clock.c \ + config_psu.c \ + config_mock_psu.c \ + config_dvfs.c \ + config_sid.c + +include $(BS_DIR)/firmware.mk diff --git a/product/sgm776/scp_ramfw/fmw_memory.ld.S b/product/sgm776/scp_ramfw/fmw_memory.ld.S new file mode 100644 index 00000000..4f062809 --- /dev/null +++ b/product/sgm776/scp_ramfw/fmw_memory.ld.S @@ -0,0 +1,21 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef FMW_MEMORY_LD_S +#define FMW_MEMORY_LD_S + +#include <system_mmap_scp.h> + +#define FIRMWARE_MEM_MODE FWK_MEM_MODE_SINGLE_REGION + +/* RAM */ +#define FIRMWARE_MEM0_BASE SCP_RAM_BASE +#define FIRMWARE_MEM0_SIZE SCP_RAM_SIZE + +#define FIRMWARE_STACK_SIZE (1 * 1024) + +#endif /* FMW_MEMORY_LD_S */ diff --git a/product/sgm776/scp_ramfw/rtx_config.c b/product/sgm776/scp_ramfw/rtx_config.c new file mode 100644 index 00000000..12842cd8 --- /dev/null +++ b/product/sgm776/scp_ramfw/rtx_config.c @@ -0,0 +1,79 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <stdbool.h> +#include <stdint.h> +#include <cmsis_compiler.h> +#include <rtx_os.h> +#include <system_clock.h> + +#include <rtx_lib.c> + +/* + * Required by RTX to configure the SysTick timer. + */ +uint32_t SystemCoreClock = CLOCK_RATE_REFCLK; + +/* + * Idle thread + */ +__NO_RETURN void osRtxIdleThread(void *argument) +{ + (void)argument; + + while (true) + __WFI(); +} + +/* + * OS error handler + */ +uint32_t osRtxErrorNotify(uint32_t code, void *object_id) +{ + (void)object_id; + + switch (code) { + case osRtxErrorStackUnderflow: + /* + * Stack underflow detected for thread + * thread_id=object_id + */ + break; + + case osRtxErrorISRQueueOverflow: + /* + * ISR Queue overflow detected when inserting object + * object_id + */ + break; + + case osRtxErrorTimerQueueOverflow: + /* + * User Timer Callback Queue overflow detected for timer + * timer_id=object_id + */ + break; + + case osRtxErrorClibSpace: + /* + * Standard C/C++ library libspace not available: + * increase OS_THREAD_LIBSPACE_NUM + */ + break; + + case osRtxErrorClibMutex: + /* + * Standard C/C++ library mutex initialization failed + */ + break; + + default: + break; + } + + osRtxIdleThread(object_id); +} diff --git a/product/sgm776/scp_romfw/clock_devices.h b/product/sgm776/scp_romfw/clock_devices.h new file mode 100644 index 00000000..be2f007a --- /dev/null +++ b/product/sgm776/scp_romfw/clock_devices.h @@ -0,0 +1,28 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef CLOCK_DEVICES_H +#define CLOCK_DEVICES_H + +/*! + * \brief Clock device indexes. + */ +enum clock_dev_idx { + CLOCK_DEV_IDX_BIG, + CLOCK_DEV_IDX_LITTLE, + CLOCK_DEV_IDX_GPU, + CLOCK_DEV_IDX_SYS_NOCMEMCLK, + CLOCK_DEV_IDX_SYS_FCMCLK, + CLOCK_DEV_IDX_SYS_GICCLK, + CLOCK_DEV_IDX_SYS_PCLKSCP, + CLOCK_DEV_IDX_SYS_SYSPERCLK, + CLOCK_DEV_IDX_PLL_SWTCLKTCK, + CLOCK_DEV_IDX_PLL_SYSTEM, + CLOCK_DEV_IDX_COUNT +}; + +#endif /* CLOCK_DEVICES_H */ diff --git a/product/sgm776/scp_romfw/config_bootloader.c b/product/sgm776/scp_romfw/config_bootloader.c new file mode 100644 index 00000000..f9177984 --- /dev/null +++ b/product/sgm776/scp_romfw/config_bootloader.c @@ -0,0 +1,26 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_element.h> +#include <fwk_macros.h> +#include <fwk_module.h> +#include <mod_bootloader.h> +#include <system_mmap.h> +#include <system_mmap_scp.h> +#include <sgm776_sds.h> + +static const struct mod_bootloader_config bootloader_module_config = { + .source_base = TRUSTED_RAM_BASE, + .source_size = 256 * 1024, + .destination_base = SCP_RAM_BASE, + .destination_size = SCP_RAM_SIZE, + .sds_struct_id = SGM776_SDS_BOOTLOADER, +}; + +struct fwk_module_config config_bootloader = { + .data = &bootloader_module_config, +}; diff --git a/product/sgm776/scp_romfw/config_clock.c b/product/sgm776/scp_romfw/config_clock.c new file mode 100644 index 00000000..0f796d0c --- /dev/null +++ b/product/sgm776/scp_romfw/config_clock.c @@ -0,0 +1,117 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <stddef.h> +#include <fwk_element.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_clock.h> +#include <mod_css_clock.h> +#include <mod_system_pll.h> +#include <mod_msys_rom.h> +#include <mod_pik_clock.h> +#include <clock_devices.h> + +static const struct fwk_element clock_dev_desc_table[] = { + [CLOCK_DEV_IDX_BIG] = { + .name = "CPU_GROUP_BIG", + .data = &((struct mod_clock_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_CSS_CLOCK, 0), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_CSS_CLOCK, + MOD_CSS_CLOCK_API_TYPE_CLOCK), + .pd_source_id = FWK_ID_MODULE_INIT(FWK_MODULE_IDX_MSYS_ROM), + }), + }, + [CLOCK_DEV_IDX_LITTLE] = { + .name = "CPU_GROUP_LITTLE", + .data = &((struct mod_clock_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_CSS_CLOCK, 1), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_CSS_CLOCK, + MOD_CSS_CLOCK_API_TYPE_CLOCK), + .pd_source_id = FWK_ID_MODULE_INIT(FWK_MODULE_IDX_MSYS_ROM), + }), + }, + [CLOCK_DEV_IDX_GPU] = { + .name = "GPU", + .data = &((struct mod_clock_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_CSS_CLOCK, 2), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_CSS_CLOCK, + MOD_CSS_CLOCK_API_TYPE_CLOCK), + .pd_source_id = FWK_ID_MODULE_INIT(FWK_MODULE_IDX_MSYS_ROM), + }), + }, + [CLOCK_DEV_IDX_SYS_NOCMEMCLK] = { + .name = "SYS_NOCMEMCLK", + .data = &((struct mod_clock_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 0), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PIK_CLOCK, + MOD_PIK_CLOCK_API_TYPE_CLOCK), + .pd_source_id = FWK_ID_MODULE_INIT(FWK_MODULE_IDX_MSYS_ROM), + }), + }, + [CLOCK_DEV_IDX_SYS_FCMCLK] = { + .name = "SYS_FCMCLK", + .data = &((struct mod_clock_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 1), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PIK_CLOCK, + MOD_PIK_CLOCK_API_TYPE_CLOCK), + .pd_source_id = FWK_ID_MODULE_INIT(FWK_MODULE_IDX_MSYS_ROM), + }), + }, + [CLOCK_DEV_IDX_SYS_GICCLK] = { + .name = "SYS_GICCLK", + .data = &((struct mod_clock_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 2), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PIK_CLOCK, + MOD_PIK_CLOCK_API_TYPE_CLOCK), + .pd_source_id = FWK_ID_MODULE_INIT(FWK_MODULE_IDX_MSYS_ROM), + }), + }, + [CLOCK_DEV_IDX_SYS_PCLKSCP] = { + .name = "SYS_PCLKSCP", + .data = &((struct mod_clock_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 3), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PIK_CLOCK, + MOD_PIK_CLOCK_API_TYPE_CLOCK), + .pd_source_id = FWK_ID_MODULE_INIT(FWK_MODULE_IDX_MSYS_ROM), + }), + }, + [CLOCK_DEV_IDX_SYS_SYSPERCLK] = { + .name = "SYS_SYSPERCLK", + .data = &((struct mod_clock_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 4), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PIK_CLOCK, + MOD_PIK_CLOCK_API_TYPE_CLOCK), + .pd_source_id = FWK_ID_MODULE_INIT(FWK_MODULE_IDX_MSYS_ROM), + }), + }, + [CLOCK_DEV_IDX_PLL_SYSTEM] = { + .name = "PLL_SYSTEM", + .data = &((struct mod_clock_dev_config) { + .driver_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_SYSTEM_PLL, 3), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_SYSTEM_PLL, + MOD_SYSTEM_PLL_API_TYPE_DEFAULT), + .pd_source_id = FWK_ID_MODULE_INIT(FWK_MODULE_IDX_MSYS_ROM), + }), + }, + [CLOCK_DEV_IDX_COUNT] = { 0 }, /* Termination description. */ +}; + +static const struct fwk_element *clock_get_dev_desc_table(fwk_id_t module_id) +{ + return clock_dev_desc_table; +} + +const struct fwk_module_config config_clock = { + .get_element_table = clock_get_dev_desc_table, + .data = &((struct mod_clock_config) { + .pd_transition_notification_id = FWK_ID_NOTIFICATION_INIT( + FWK_MODULE_IDX_MSYS_ROM, + MOD_MSYS_ROM_NOTIFICATION_IDX_POWER_SYSTOP), + .pd_pre_transition_notification_id = FWK_ID_NONE_INIT, + }), +}; diff --git a/product/sgm776/scp_romfw/config_css_clock.c b/product/sgm776/scp_romfw/config_css_clock.c new file mode 100644 index 00000000..69b50e20 --- /dev/null +++ b/product/sgm776/scp_romfw/config_css_clock.c @@ -0,0 +1,186 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_assert.h> +#include <fwk_element.h> +#include <fwk_macros.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_css_clock.h> +#include <mod_system_pll.h> +#include <mod_pik_clock.h> +#include <mod_sid.h> + +static const struct mod_css_clock_rate rate_table_cpu_group_big[] = { + { + .rate = 2700 * FWK_MHZ, + .pll_rate = 2700 * FWK_MHZ, + .clock_source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_PLL1, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + .clock_mod_numerator = 1, + .clock_mod_denominator = 1, + }, +}; + +static const struct mod_css_clock_rate rate_table_cpu_group_little[] = { + { + .rate = 2200 * FWK_MHZ, + .pll_rate = 2200 * FWK_MHZ, + .clock_source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_PLL0, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + .clock_mod_numerator = 1, + .clock_mod_denominator = 1, + }, +}; + +static const struct mod_css_clock_rate rate_table_gpu[] = { + { + .rate = 800 * FWK_MHZ, + .pll_rate = 800 * FWK_MHZ, + .clock_source = MOD_PIK_CLOCK_MSCLOCK_SOURCE_PRIVPLLCLK, + .clock_div_type = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .clock_div = 1, + }, +}; + +static const fwk_id_t member_table_cpu_big_cfg_a[] = { + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 11), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 12), +}; + +static const fwk_id_t member_table_cpu_little_cfg_a[] = { + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 5), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 6), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 7), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 8), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 9), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 10), +}; + +static const fwk_id_t member_table_cpu_big_cfg_b[] = { + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 9), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 10), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 11), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 12), +}; + +static const fwk_id_t member_table_cpu_little_cfg_b[] = { + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 5), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 6), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 7), + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 8), +}; + +static const fwk_id_t member_table_gpu[] = { + FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PIK_CLOCK, 13), +}; + +static const struct fwk_element css_clock_element_table[] = { + { + .name = "CPU_GROUP_BIG", + .data = &((struct mod_css_clock_dev_config) { + .rate_table = rate_table_cpu_group_big, + .rate_count = sizeof(rate_table_cpu_group_big) / + sizeof(struct mod_css_clock_rate), + .clock_switching_source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_SYSREFCLK, + .pll_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_SYSTEM_PLL, 1), + .pll_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_SYSTEM_PLL, + MOD_SYSTEM_PLL_API_TYPE_DEFAULT), + .member_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PIK_CLOCK, + MOD_PIK_CLOCK_API_TYPE_CSS), + .initial_rate = 2700 * FWK_MHZ, + .modulation_supported = true, + }), + }, + { + .name = "CPU_GROUP_LITTLE", + .data = &((struct mod_css_clock_dev_config) { + .rate_table = rate_table_cpu_group_little, + .rate_count = sizeof(rate_table_cpu_group_little) / + sizeof(struct mod_css_clock_rate), + .clock_switching_source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_SYSREFCLK, + .pll_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_SYSTEM_PLL, 0), + .pll_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_SYSTEM_PLL, + MOD_SYSTEM_PLL_API_TYPE_DEFAULT), + .member_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PIK_CLOCK, + MOD_PIK_CLOCK_API_TYPE_CSS), + .initial_rate = 2200 * FWK_MHZ, + .modulation_supported = true, + }), + }, + { + .name = "GPU", + .data = &((struct mod_css_clock_dev_config) { + .rate_table = rate_table_gpu, + .rate_count = sizeof(rate_table_gpu) / + sizeof(struct mod_css_clock_rate), + .clock_switching_source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_SYSREFCLK, + .pll_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_SYSTEM_PLL, 2), + .pll_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_SYSTEM_PLL, + MOD_SYSTEM_PLL_API_TYPE_DEFAULT), + .member_table = member_table_gpu, + .member_count = FWK_ARRAY_SIZE(member_table_gpu), + .member_api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PIK_CLOCK, + MOD_PIK_CLOCK_API_TYPE_CSS), + .initial_rate = 800 * FWK_MHZ, + .modulation_supported = false, + }), + }, + { 0 }, /* Termination description. */ +}; + +static const struct fwk_element *css_clock_get_element_table + (fwk_id_t module_id) +{ + int status; + struct mod_css_clock_dev_config *config_big; + struct mod_css_clock_dev_config *config_little; + const struct mod_sid_info *system_info; + + status = mod_sid_get_system_info(&system_info); + fwk_assert(status == FWK_SUCCESS); + + config_big = + (struct mod_css_clock_dev_config *) css_clock_element_table[0].data; + config_little = + (struct mod_css_clock_dev_config *) css_clock_element_table[1].data; + + switch (system_info->config_number) { + case 1: + case 5: + case 7: + case 8: + config_big->member_table = member_table_cpu_big_cfg_a; + config_big->member_count = FWK_ARRAY_SIZE(member_table_cpu_big_cfg_a); + + config_little->member_table = member_table_cpu_little_cfg_a; + config_little->member_count = + FWK_ARRAY_SIZE(member_table_cpu_little_cfg_a); + break; + case 2: + case 3: + case 4: + case 6: + config_big->member_table = member_table_cpu_big_cfg_b; + config_big->member_count = FWK_ARRAY_SIZE(member_table_cpu_big_cfg_b); + + config_little->member_table = member_table_cpu_little_cfg_b; + config_little->member_count = + FWK_ARRAY_SIZE(member_table_cpu_little_cfg_b); + break; + default: + return NULL; + } + + return css_clock_element_table; +} + +const struct fwk_module_config config_css_clock = { + .get_element_table = css_clock_get_element_table, +}; diff --git a/product/sgm776/scp_romfw/config_log.c b/product/sgm776/scp_romfw/config_log.c new file mode 100644 index 00000000..29fdf358 --- /dev/null +++ b/product/sgm776/scp_romfw/config_log.c @@ -0,0 +1,62 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_banner.h> +#include <fwk_macros.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_clock.h> +#include <mod_log.h> +#include <mod_pl011.h> +#include <system_mmap.h> +#include <clock_devices.h> + +/* + * PL011 module + */ +static const struct fwk_element pl011_element_desc_table[] = { + [0] = { + .name = "board-uart1", + .data = &((struct mod_pl011_device_config) { + .reg_base = BOARD_UART1_BASE, + .baud_rate_bps = 115200, + .clock_rate_hz = 24 * FWK_MHZ, + .clock_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_CLOCK, + CLOCK_DEV_IDX_SYS_NOCMEMCLK), + }), + }, + [1] = { 0 }, +}; + +static const struct fwk_element *get_pl011_table(fwk_id_t module_id) +{ + return pl011_element_desc_table; +} + +struct fwk_module_config config_pl011 = { + .get_element_table = get_pl011_table, +}; + +/* + * Log module + */ +static const struct mod_log_config log_data = { + .device_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PL011, 0), + .api_id = FWK_ID_API_INIT(FWK_MODULE_IDX_PL011, 0), + .log_groups = MOD_LOG_GROUP_ERROR | + MOD_LOG_GROUP_INFO | + MOD_LOG_GROUP_WARNING | + MOD_LOG_GROUP_DEBUG, + .banner = FWK_BANNER_SCP + FWK_BANNER_ROM_FIRMWARE + BUILD_VERSION_DESCRIBE_STRING "\n", +}; + +struct fwk_module_config config_log = { + .get_element_table = NULL, + .data = &log_data, +}; diff --git a/product/sgm776/scp_romfw/config_msys_rom.c b/product/sgm776/scp_romfw/config_msys_rom.c new file mode 100644 index 00000000..1e38f1b1 --- /dev/null +++ b/product/sgm776/scp_romfw/config_msys_rom.c @@ -0,0 +1,23 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_id.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_msys_rom.h> +#include <sgm776_mmap_scp.h> +#include <software_mmap.h> + +const struct fwk_module_config config_msys_rom = { + .data = &((struct msys_rom_config) { + .ap_context_base = AP_CONTEXT_BASE, + .ap_context_size = AP_CONTEXT_SIZE, + .ramfw_base = SCP_RAM_BASE, + .id_primary_cluster = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PPU_V1, 2), + .id_primary_core = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PPU_V1, 3), + }) +}; diff --git a/product/sgm776/scp_romfw/config_pik_clock.c b/product/sgm776/scp_romfw/config_pik_clock.c new file mode 100644 index 00000000..f42d2d1b --- /dev/null +++ b/product/sgm776/scp_romfw/config_pik_clock.c @@ -0,0 +1,341 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_assert.h> +#include <fwk_element.h> +#include <fwk_macros.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_pik_clock.h> +#include <mod_sid.h> +#include <sgm776_pik.h> +#include <system_clock.h> + +/* + * Rate lookup tables. + */ + +static const struct mod_pik_clock_rate rate_table_sys_nocmemclk[] = { + { + .rate = 720 * FWK_MHZ, + .source = MOD_PIK_CLOCK_MSCLOCK_SOURCE_SYSPLLCLK, + .divider_reg = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_SYS, + .divider = CLOCK_RATE_SYSPLLCLK / (720 * FWK_MHZ), + }, +}; + +static const struct mod_pik_clock_rate rate_table_sys_fcmclk[] = { + { + .rate = 1800 * FWK_MHZ, + .source = MOD_PIK_CLOCK_MSCLOCK_SOURCE_SYSPLLCLK, + .divider_reg = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_SYS, + .divider = CLOCK_RATE_SYSPLLCLK / (1800 * FWK_MHZ), + }, +}; + +static const struct mod_pik_clock_rate rate_table_sys_gicclk[] = { + { + .rate = 600 * FWK_MHZ, + .source = MOD_PIK_CLOCK_MSCLOCK_SOURCE_SYSPLLCLK, + .divider_reg = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_SYS, + .divider = CLOCK_RATE_SYSPLLCLK / (600 * FWK_MHZ), + }, +}; + +static const struct mod_pik_clock_rate rate_table_sys_pclkscp[] = { + { + .rate = 225 * FWK_MHZ, + .source = MOD_PIK_CLOCK_MSCLOCK_SOURCE_SYSPLLCLK, + .divider_reg = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_SYS, + .divider = CLOCK_RATE_SYSPLLCLK / (225 * FWK_MHZ), + }, +}; + +static const struct mod_pik_clock_rate rate_table_sys_sysperclk[] = { + { + .rate = 225 * FWK_MHZ, + .source = MOD_PIK_CLOCK_MSCLOCK_SOURCE_SYSPLLCLK, + .divider_reg = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_SYS, + .divider = CLOCK_RATE_SYSPLLCLK / (225 * FWK_MHZ), + }, +}; + +static const struct mod_pik_clock_rate rate_table_cpu_a55[] = { + { + .rate = 2200 * FWK_MHZ, + .source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_PLL0, + .divider_reg = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .divider = 1, /* Rate adjusted via CPU PLL */ + }, +}; + +static const struct mod_pik_clock_rate rate_table_cpu_a75[] = { + { + .rate = 2700 * FWK_MHZ, + .source = MOD_PIK_CLOCK_CLUSCLK_SOURCE_PLL1, + .divider_reg = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .divider = 1, /* Rate adjusted via CPU PLL */ + }, +}; + +static const struct mod_pik_clock_rate rate_table_gpu[] = { + { + .rate = 800 * FWK_MHZ, + .source = MOD_PIK_CLOCK_MSCLOCK_SOURCE_PRIVPLLCLK, + .divider_reg = MOD_PIK_CLOCK_MSCLOCK_DIVIDER_DIV_EXT, + .divider = 1, /* Rate adjusted via GPU PLL */ + }, +}; + +static const struct fwk_element pik_clock_element_table[] = { + /* + * System Clocks + */ + { + .name = "SYS_NOCMEMCLK", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_MULTI_SOURCE, + .is_group_member = false, + .control_reg = &PIK_SYSTEM->NOCMEMCLK_CTRL, + .divsys_reg = &PIK_SYSTEM->NOCMEMCLK_DIV1, + .rate_table = rate_table_sys_nocmemclk, + .rate_count = FWK_ARRAY_SIZE(rate_table_sys_nocmemclk), + .initial_rate = 720 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "SYS_FCMCLK", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_MULTI_SOURCE, + .is_group_member = false, + .control_reg = &PIK_SYSTEM->FCMCLK_CTRL, + .divsys_reg = &PIK_SYSTEM->FCMCLK_DIV1, + .rate_table = rate_table_sys_fcmclk, + .rate_count = FWK_ARRAY_SIZE(rate_table_sys_fcmclk), + .initial_rate = 1800 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "SYS_GICCLK", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_MULTI_SOURCE, + .is_group_member = false, + .control_reg = &PIK_SYSTEM->GICCLK_CTRL, + .divsys_reg = &PIK_SYSTEM->GICCLK_DIV1, + .rate_table = rate_table_sys_gicclk, + .rate_count = FWK_ARRAY_SIZE(rate_table_sys_gicclk), + .initial_rate = 600 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "SYS_PCLKSCP", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_MULTI_SOURCE, + .is_group_member = false, + .control_reg = &PIK_SYSTEM->PCLKSCP_CTRL, + .divsys_reg = &PIK_SYSTEM->PCLKSCP_DIV1, + .rate_table = rate_table_sys_pclkscp, + .rate_count = FWK_ARRAY_SIZE(rate_table_sys_pclkscp), + .initial_rate = 225 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "SYS_SYSPERCLK", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_MULTI_SOURCE, + .is_group_member = false, + .control_reg = &PIK_SYSTEM->SYSPERCLK_CTRL, + .divsys_reg = &PIK_SYSTEM->SYSPERCLK_DIV1, + .rate_table = rate_table_sys_sysperclk, + .rate_count = FWK_ARRAY_SIZE(rate_table_sys_sysperclk), + .initial_rate = 225 * FWK_MHZ, + .defer_initialization = true, + }), + }, + /* + * Cluster 0 CPUs + */ + { + .name = "CLUS0_CPU0", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_CLUSTER, + .is_group_member = true, + .control_reg = &PIK_CLUS0->CORECLK[0].CTRL, + .divext_reg = &PIK_CLUS0->CORECLK[0].DIV, + .modulator_reg = &PIK_CLUS0->CORECLK[0].MOD, + .initial_rate = 2200 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "CLUS0_CPU1", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_CLUSTER, + .is_group_member = true, + .control_reg = &PIK_CLUS0->CORECLK[1].CTRL, + .divext_reg = &PIK_CLUS0->CORECLK[1].DIV, + .modulator_reg = &PIK_CLUS0->CORECLK[1].MOD, + .initial_rate = 2200 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "CLUS0_CPU2", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_CLUSTER, + .is_group_member = true, + .control_reg = &PIK_CLUS0->CORECLK[2].CTRL, + .divext_reg = &PIK_CLUS0->CORECLK[2].DIV, + .modulator_reg = &PIK_CLUS0->CORECLK[2].MOD, + .initial_rate = 2200 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "CLUS0_CPU3", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_CLUSTER, + .is_group_member = true, + .control_reg = &PIK_CLUS0->CORECLK[3].CTRL, + .divext_reg = &PIK_CLUS0->CORECLK[3].DIV, + .modulator_reg = &PIK_CLUS0->CORECLK[3].MOD, + .initial_rate = 2200 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "CLUS0_CPU4", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_CLUSTER, + .is_group_member = true, + .control_reg = &PIK_CLUS0->CORECLK[4].CTRL, + .divext_reg = &PIK_CLUS0->CORECLK[4].DIV, + .modulator_reg = &PIK_CLUS0->CORECLK[4].MOD, + .initial_rate = 2700 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "CLUS0_CPU5", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_CLUSTER, + .is_group_member = true, + .control_reg = &PIK_CLUS0->CORECLK[5].CTRL, + .divext_reg = &PIK_CLUS0->CORECLK[5].DIV, + .modulator_reg = &PIK_CLUS0->CORECLK[5].MOD, + .initial_rate = 2700 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "CLUS0_CPU6", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_CLUSTER, + .is_group_member = true, + .control_reg = &PIK_CLUS0->CORECLK[6].CTRL, + .divext_reg = &PIK_CLUS0->CORECLK[6].DIV, + .modulator_reg = &PIK_CLUS0->CORECLK[6].MOD, + .initial_rate = 2700 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { + .name = "CLUS0_CPU7", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_CLUSTER, + .is_group_member = true, + .control_reg = &PIK_CLUS0->CORECLK[7].CTRL, + .divext_reg = &PIK_CLUS0->CORECLK[7].DIV, + .modulator_reg = &PIK_CLUS0->CORECLK[7].MOD, + .initial_rate = 2700 * FWK_MHZ, + .defer_initialization = true, + }), + }, + /* + * GPU + */ + { + .name = "GPU", + .data = &((struct mod_pik_clock_dev_config) { + .type = MOD_PIK_CLOCK_TYPE_MULTI_SOURCE, + .is_group_member = true, + .control_reg = &PIK_GPU->GPUCLK_CTRL, + .divsys_reg = &PIK_GPU->GPUCLK_DIV1, + .divext_reg = &PIK_GPU->GPUCLK_DIV2, + .rate_table = rate_table_gpu, + .rate_count = FWK_ARRAY_SIZE(rate_table_gpu), + .initial_rate = 800 * FWK_MHZ, + .defer_initialization = true, + }), + }, + { 0 }, /* Termination description. */ +}; + +static const struct fwk_element *pik_clock_get_element_table + (fwk_id_t module_id) +{ + int status; + int element_idx; + struct mod_pik_clock_dev_config *config; + const struct mod_sid_info *system_info; + + status = mod_sid_get_system_info(&system_info); + fwk_assert(status == FWK_SUCCESS); + + switch (system_info->config_number) { + case 1: + case 5: + case 7: + case 8: + /* CPUs 0-5: Little */ + for (element_idx = 5; element_idx < 11; element_idx++) { + config = (struct mod_pik_clock_dev_config *) + pik_clock_element_table[element_idx].data; + config->rate_table = rate_table_cpu_a55; + config->rate_count = FWK_ARRAY_SIZE(rate_table_cpu_a55); + } + /* CPUs 6-7: Big */ + for (element_idx = 11; element_idx < 13; element_idx++) { + config = (struct mod_pik_clock_dev_config *) + pik_clock_element_table[element_idx].data; + config->rate_table = rate_table_cpu_a75; + config->rate_count = FWK_ARRAY_SIZE(rate_table_cpu_a75); + } + break; + case 2: + case 3: + case 4: + case 6: + /* CPUs 0-3: Little */ + for (element_idx = 5; element_idx < 9; element_idx++) { + config = (struct mod_pik_clock_dev_config *) + pik_clock_element_table[element_idx].data; + config->rate_table = rate_table_cpu_a55; + config->rate_count = FWK_ARRAY_SIZE(rate_table_cpu_a55); + } + /* CPUs 4-7: Big */ + for (element_idx = 9; element_idx < 13; element_idx++) { + config = (struct mod_pik_clock_dev_config *) + pik_clock_element_table[element_idx].data; + config->rate_table = rate_table_cpu_a75; + config->rate_count = FWK_ARRAY_SIZE(rate_table_cpu_a75); + } + break; + default: + return NULL; + } + + return pik_clock_element_table; +} + +const struct fwk_module_config config_pik_clock = { + .get_element_table = pik_clock_get_element_table, +}; diff --git a/product/sgm776/scp_romfw/config_ppu_v1.c b/product/sgm776/scp_romfw/config_ppu_v1.c new file mode 100644 index 00000000..3d12d9cc --- /dev/null +++ b/product/sgm776/scp_romfw/config_ppu_v1.c @@ -0,0 +1,77 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <stddef.h> +#include <fwk_element.h> +#include <fwk_mm.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_msys_rom.h> +#include <mod_ppu_v1.h> +#include <sgm776_irq.h> +#include <sgm776_mmap.h> + +static struct fwk_element sgm776_ppu_v1_element_table[] = { + { + .name = "SYS0", + .data = &((struct mod_ppu_v1_pd_config) { + .pd_type = MOD_PD_TYPE_SYSTEM, + .ppu.reg_base = PPU_SYS0_BASE, + .ppu.irq = PPU_SYS0_IRQ, + .default_power_on = true, + .observer_id = FWK_ID_NONE_INIT, + }), + }, + { + .name = "SYS1", + .data = &((struct mod_ppu_v1_pd_config) { + .pd_type = MOD_PD_TYPE_SYSTEM, + .ppu.reg_base = PPU_SYS1_BASE, + .ppu.irq = PPU_SYS1_IRQ, + .default_power_on = true, + .observer_id = FWK_ID_NONE_INIT, + }), + }, + { + .name = "CLUS0", + .data = &((struct mod_ppu_v1_pd_config) { + .pd_type = MOD_PD_TYPE_CLUSTER, + .ppu.reg_base = PPU_CLUS0_BASE, + .ppu.irq = PPU_CLUS0_IRQ, + .observer_id = FWK_ID_NONE_INIT, + }), + }, + { + .name = "CORE0", + .data = &((struct mod_ppu_v1_pd_config) { + .pd_type = MOD_PD_TYPE_CORE, + .ppu.reg_base = PPU_CLUS0CORE0_BASE, + .ppu.irq = PPU_CLUS0CORE0_IRQ, + .cluster_id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_PPU_V1, 2), + .observer_id = FWK_ID_NONE_INIT, + }), + }, + { 0 }, /* Termination entry */ +}; + +static const struct fwk_element *sgm776_ppu_v1_get_element_table( + fwk_id_t module_id) +{ + return sgm776_ppu_v1_element_table; +} + +/* + * Power module configuration data + */ +struct fwk_module_config config_ppu_v1 = { + .get_element_table = sgm776_ppu_v1_get_element_table, + .data = &(struct mod_ppu_v1_config) { + .pd_notification_id = FWK_ID_NOTIFICATION_INIT(FWK_MODULE_IDX_MSYS_ROM, + MOD_MSYS_ROM_NOTIFICATION_IDX_POWER_SYSTOP), + .pd_source_id = FWK_ID_MODULE_INIT(FWK_MODULE_IDX_MSYS_ROM), + }, +}; diff --git a/product/sgm776/scp_romfw/config_sds.c b/product/sgm776/scp_romfw/config_sds.c new file mode 100644 index 00000000..ffae2b24 --- /dev/null +++ b/product/sgm776/scp_romfw/config_sds.c @@ -0,0 +1,126 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_assert.h> +#include <stdint.h> +#include <fwk_element.h> +#include <fwk_macros.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_sds.h> +#include <mod_sid.h> +#include <sgm776_mmap.h> +#include <sgm776_sds.h> +#include <sgm776_pik.h> +#include <system_mmap.h> +#include <clock_devices.h> + +static const uint32_t version_packed = FWK_BUILD_VERSION; +static struct sgm776_sds_platid platid; + +static const struct mod_sds_config sds_module_config = { + .region_base_address = TRUSTED_RAM_BASE, + .region_size = 3520, + .clock_id = FWK_ID_ELEMENT_INIT( + FWK_MODULE_IDX_CLOCK, + CLOCK_DEV_IDX_SYS_NOCMEMCLK), +}; + +static const struct fwk_element sds_element_table[] = { + { + .name = "CPU Info", + .data = &((struct mod_sds_structure_desc) { + .id = SGM776_SDS_CPU_INFO, + .size = SGM776_SDS_CPU_INFO_SIZE, + .finalize = true, + }), + }, + { + .name = "ROM Version", + .data = &((struct mod_sds_structure_desc) { + .id = SGM776_SDS_ROM_VERSION, + .size = SGM776_SDS_ROM_VERSION_SIZE, + .payload = &version_packed, + .finalize = true, + }), + }, + { + .name = "Platform ID", + .data = &((struct mod_sds_structure_desc) { + .id = SGM776_SDS_PLATFORM_ID, + .size = SGM776_SDS_PLATFORM_ID_SIZE, + .payload = &platid, + .finalize = true, + }), + }, + { + .name = "Reset Syndrome", + .data = &((struct mod_sds_structure_desc) { + .id = SGM776_SDS_RESET_SYNDROME, + .size = SGM776_SDS_RESET_SYNDROME_SIZE, + .payload = (const void *)&PIK_SCP->RESET_SYNDROME, + .finalize = true, + }), + }, + { + .name = "Bootloader", + .data = &((struct mod_sds_structure_desc) { + .id = SGM776_SDS_BOOTLOADER, + .size = SGM776_SDS_BOOTLOADER_SIZE, + .finalize = true, + }), + }, + { + .name = "Features", + .data = &((struct mod_sds_structure_desc) { + .id = SGM776_SDS_FEATURE_AVAILABILITY, + .size = SGM776_SDS_FEATURE_AVAILABILITY_SIZE, + .finalize = true, + }), + }, +#ifdef MODE_DEBUG + { + .name = "Boot Counters", + .data = &((struct mod_sds_structure_desc) { + .id = SGM776_SDS_CPU_BOOTCTR, + .size = SGM776_SDS_CPU_BOOTCTR_SIZE, + .finalize = true, + }), + }, + { + .name = "CPU Flags", + .data = &((struct mod_sds_structure_desc) { + .id = SGM776_SDS_CPU_FLAGS, + .size = SGM776_SDS_CPU_FLAGS_SIZE, + .finalize = true, + }), + }, +#endif + { 0 }, /* Termination description. */ +}; + +static const struct fwk_element *sds_get_element_table(fwk_id_t module_id) +{ + int status; + const struct mod_sid_info *system_info; + + static_assert(BUILD_VERSION_MAJOR < UINT8_MAX, "Invalid version size"); + static_assert(BUILD_VERSION_MINOR < UINT8_MAX, "Invalid version size"); + static_assert(BUILD_VERSION_PATCH < UINT16_MAX, "Invalid version size"); + + status = mod_sid_get_system_info(&system_info); + fwk_assert(status == FWK_SUCCESS); + platid.platform_identifier = system_info->system_part_number; + platid.platform_type_identifier = *((uint32_t*)PLATFORM_ID); + + return sds_element_table; +} + +struct fwk_module_config config_sds = { + .get_element_table = sds_get_element_table, + .data = &sds_module_config, +}; diff --git a/product/sgm776/scp_romfw/config_system_pll.c b/product/sgm776/scp_romfw/config_system_pll.c new file mode 100644 index 00000000..01beaf6c --- /dev/null +++ b/product/sgm776/scp_romfw/config_system_pll.c @@ -0,0 +1,79 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2015-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_element.h> +#include <fwk_macros.h> +#include <fwk_module.h> +#include <mod_system_pll.h> +#include <sgm776_pik.h> +#include <system_mmap.h> + +static const struct fwk_element system_pll_element_table[] = { + { + .name = "CPU_PLL_0", + .data = &((struct mod_system_pll_dev_config) { + .control_reg = (void *)PLL_CLUS0_0, + .status_reg = (void *)&PIK_SCP->PLL_STATUS1, + .lock_flag_mask = PLL_STATUS1_CPUPLLLOCK(0, 0), + .initial_rate = 2700 * FWK_MHZ, + .min_rate = MOD_SYSTEM_PLL_MIN_RATE, + .max_rate = MOD_SYSTEM_PLL_MAX_RATE, + .min_step = MOD_SYSTEM_PLL_MIN_INTERVAL, + .defer_initialization = false, + }), + }, + { + .name = "CPU_PLL_1", + .data = &((struct mod_system_pll_dev_config) { + .control_reg = (void *)PLL_CLUS0_1, + .status_reg = (void *)&PIK_SCP->PLL_STATUS1, + .lock_flag_mask = PLL_STATUS1_CPUPLLLOCK(0, 1), + .initial_rate = 2200 * FWK_MHZ, + .min_rate = MOD_SYSTEM_PLL_MIN_RATE, + .max_rate = MOD_SYSTEM_PLL_MAX_RATE, + .min_step = MOD_SYSTEM_PLL_MIN_INTERVAL, + .defer_initialization = false, + }), + }, + { + .name = "GPU_PLL", + .data = &((struct mod_system_pll_dev_config) { + .control_reg = (void *)PLL_GPU, + .status_reg = (void *)&PIK_SCP->PLL_STATUS0, + .lock_flag_mask = PLL_STATUS0_GPUPLLLOCK, + .initial_rate = 800 * FWK_MHZ, + .min_rate = MOD_SYSTEM_PLL_MIN_RATE, + .max_rate = MOD_SYSTEM_PLL_MAX_RATE, + .min_step = MOD_SYSTEM_PLL_MIN_INTERVAL, + .defer_initialization = false, + }), + }, + { + .name = "SYS_PLL", + .data = &((struct mod_system_pll_dev_config) { + .control_reg = (void *)PLL_SYSTEM, + .status_reg = (void *)&PIK_SCP->PLL_STATUS0, + .lock_flag_mask = PLL_STATUS0_SYSPLLLOCK, + .initial_rate = 3600 * FWK_MHZ, + .min_rate = MOD_SYSTEM_PLL_MIN_RATE, + .max_rate = MOD_SYSTEM_PLL_MAX_RATE, + .min_step = MOD_SYSTEM_PLL_MIN_INTERVAL, + .defer_initialization = false, + }), + }, + { 0 }, /* Termination description. */ +}; + +static const struct fwk_element *system_pll_get_element_table + (fwk_id_t module_id) +{ + return system_pll_element_table; +} + +const struct fwk_module_config config_system_pll = { + .get_element_table = system_pll_get_element_table, +}; diff --git a/product/sgm776/scp_romfw/config_timer.c b/product/sgm776/scp_romfw/config_timer.c new file mode 100644 index 00000000..62d2d523 --- /dev/null +++ b/product/sgm776/scp_romfw/config_timer.c @@ -0,0 +1,68 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_id.h> +#include <fwk_module.h> +#include <fwk_module_idx.h> +#include <mod_clock.h> +#include <mod_gtimer.h> +#include <mod_timer.h> +#include <sgm776_mmap.h> +#include <clock_devices.h> +#include <system_clock.h> + +/* + * Generic timer driver config + */ +static const struct fwk_element gtimer_dev_table[] = { + [0] = { + .name = "REFCLK", + .data = &((struct mod_gtimer_dev_config) { + .hw_timer = REFCLK_CNTBASE0_BASE, + .hw_counter = REFCLK_CNTCTL_BASE, + .control = REFCLK_CNTCONTROL_BASE, + .frequency = CLOCK_RATE_REFCLK, + .clock_id = FWK_ID_ELEMENT_INIT( + FWK_MODULE_IDX_CLOCK, + CLOCK_DEV_IDX_SYS_NOCMEMCLK), + }) + }, + [1] = { 0 }, +}; + +static const struct fwk_element *gtimer_get_dev_table(fwk_id_t module_id) +{ + return gtimer_dev_table; +} + +struct fwk_module_config config_gtimer = { + .get_element_table = gtimer_get_dev_table, +}; + +/* + * Timer HAL config + */ +static const struct mod_timer_dev_config refclk_config = { + .id = FWK_ID_ELEMENT_INIT(FWK_MODULE_IDX_GTIMER, 0), +}; + +static const struct fwk_element timer_dev_table[] = { + [0] = { + .name = "REFCLK", + .data = &refclk_config, + }, + [1] = { 0 }, +}; + +static const struct fwk_element *timer_get_dev_table(fwk_id_t module_id) +{ + return timer_dev_table; +} + +struct fwk_module_config config_timer = { + .get_element_table = timer_get_dev_table, +}; diff --git a/product/sgm776/scp_romfw/firmware.mk b/product/sgm776/scp_romfw/firmware.mk new file mode 100644 index 00000000..8ab120c7 --- /dev/null +++ b/product/sgm776/scp_romfw/firmware.mk @@ -0,0 +1,45 @@ +# +# Arm SCP/MCP Software +# Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. +# +# SPDX-License-Identifier: BSD-3-Clause +# + +BS_FIRMWARE_CPU := cortex-m3 +BS_FIRMWARE_HAS_MULTITHREADING := no +BS_FIRMWARE_HAS_NOTIFICATION := yes + +BS_FIRMWARE_MODULE_HEADERS_ONLY := \ + power_domain \ + timer + +BS_FIRMWARE_MODULES := \ + sid \ + pcid \ + ppu_v1 \ + pl011 \ + log \ + gtimer \ + msys_rom \ + sds \ + bootloader \ + system_pll \ + pik_clock \ + css_clock \ + clock + +BS_FIRMWARE_SOURCES := \ + sgm776_core.c \ + config_log.c \ + config_timer.c \ + config_msys_rom.c \ + config_sds.c \ + config_bootloader.c \ + config_ppu_v1.c \ + config_system_pll.c \ + config_pik_clock.c \ + config_css_clock.c \ + config_clock.c \ + config_sid.c + +include $(BS_DIR)/firmware.mk diff --git a/product/sgm776/scp_romfw/fmw_memory.ld.S b/product/sgm776/scp_romfw/fmw_memory.ld.S new file mode 100644 index 00000000..07b5ffe8 --- /dev/null +++ b/product/sgm776/scp_romfw/fmw_memory.ld.S @@ -0,0 +1,36 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + * + * Description: + * ROM firmware memory layout for the linker script. + */ + +#ifndef FMW_MEMORY_LD_S +#define FMW_MEMORY_LD_S + +#include <system_mmap_scp.h> + +#define FIRMWARE_MEM_MODE FWK_MEM_MODE_DUAL_REGION_RELOCATION + +/* + * ROM memory + */ +#define FIRMWARE_MEM0_SIZE SCP_ROM_SIZE +#define FIRMWARE_MEM0_BASE SCP_ROM_BASE + +/* + * RAM memory (16 KiB block at the top of the RAM) + * + * Note: The sections that must go into the RAM memory (i.e. stack, heap, bss + * and data) are placed at the end of the RAM memory to avoid being overwritten + * by the bootloader when loading the RAM firmware image. + */ +#define FIRMWARE_MEM1_SIZE (16 * 1024) +#define FIRMWARE_MEM1_BASE (SCP_RAM_BASE + SCP_RAM_SIZE - FIRMWARE_MEM1_SIZE) + +#define FIRMWARE_STACK_SIZE (1 * 1024) + +#endif /* FMW_MEMORY_LD_S */ diff --git a/product/sgm776/src/config_sid.c b/product/sgm776/src/config_sid.c new file mode 100644 index 00000000..8cd12d71 --- /dev/null +++ b/product/sgm776/src/config_sid.c @@ -0,0 +1,50 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <fwk_element.h> +#include <fwk_module.h> +#include <mod_sid.h> +#include <sgm776_mmap.h> +#include <sgm776_sid.h> + +static const struct fwk_element subsystem_table[] = { + { + .name = "Duke", + .data = &(struct mod_sid_subsystem_config) { + .part_number = SGM776_SID_PART_DUKE, + } + }, + { + .name = "Davis", + .data = &(struct mod_sid_subsystem_config) { + .part_number = SGM776_SID_PART_DAVIS, + } + }, + { 0 }, +}; + +static const struct fwk_element *get_subsystem_table(fwk_id_t id) +{ + return subsystem_table; +} + +struct fwk_module_config config_sid = { + .get_element_table = get_subsystem_table, + .data = &(struct mod_sid_config) { + .sid_base = SID_BASE, + .pcid_expected = { + .PID0 = 0xB9, + .PID1 = 0xB0, + .PID2 = 0x0B, + .PID4 = 0x04, + .CID0 = 0x0D, + .CID1 = 0xF0, + .CID2 = 0x05, + .CID3 = 0xB1, + }, + }, +}; diff --git a/product/sgm776/src/sgm776_core.c b/product/sgm776/src/sgm776_core.c new file mode 100644 index 00000000..d78df954 --- /dev/null +++ b/product/sgm776/src/sgm776_core.c @@ -0,0 +1,14 @@ +/* + * Arm SCP/MCP Software + * Copyright (c) 2017-2020, Arm Limited and Contributors. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <sgm776_pik.h> +#include <sgm776_core.h> + +unsigned int sgm776_core_get_count(void) +{ + return (PIK_CLUS0->PCL_CONFIG & PIK_CPU_PCL_CONFIG_NO_OF_PPU) - 1; +} diff --git a/tools/ci.py b/tools/ci.py index b61e80c6..ed359da6 100755 --- a/tools/ci.py +++ b/tools/ci.py @@ -297,6 +297,40 @@ def main(): result = subprocess.call(cmd, shell=True) results.append(('Product synquacer debug build (ARM)', result)) + banner('Test building sgm776 product') + + cmd = \ + 'CC=arm-none-eabi-gcc ' \ + 'PRODUCT=sgm776 ' \ + 'MODE=release ' \ + 'make clean all' + result = subprocess.call(cmd, shell=True) + results.append(('Product sgm776 release build (GCC)', result)) + + cmd = \ + 'CC=armclang ' \ + 'PRODUCT=sgm776 ' \ + 'MODE=release ' \ + 'make clean all' + result = subprocess.call(cmd, shell=True) + results.append(('Product sgm776 release build (ARM)', result)) + + cmd = \ + 'CC=arm-none-eabi-gcc ' \ + 'PRODUCT=sgm776 ' \ + 'MODE=debug ' \ + 'make clean all' + result = subprocess.call(cmd, shell=True) + results.append(('Product sgm776 debug build (GCC)', result)) + + cmd = \ + 'CC=armclang ' \ + 'PRODUCT=sgm776 ' \ + 'MODE=debug ' \ + 'make clean all' + result = subprocess.call(cmd, shell=True) + results.append(('Product sgm776 debug build (ARM)', result)) + banner('Tests summary') total_success = 0 |