123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271 |
- /*
- * Copyright (c) 2024 HPMicro
- *
- * SPDX-License-Identifier: BSD-3-Clause
- *
- */
- /*---------------------------------------------------------------------
- * Include
- *---------------------------------------------------------------------
- */
- #include "hpm_ppi.h"
- #include "hpm_clock_drv.h"
- static uint32_t ppi_ns2cycle(uint32_t ns)
- {
- uint32_t ppi_freq = clock_get_frequency(clock_ppi0);
- uint32_t max_cycle = PPI_CMD_CMD_CFG_CYCLE_NUM_MASK >> PPI_CMD_CMD_CFG_CYCLE_NUM_SHIFT;
- uint32_t ns_per_cycle;
- uint32_t cycle;
- ns_per_cycle = 1000000000 / ppi_freq;
- cycle = ns / ns_per_cycle;
- if (cycle > max_cycle) {
- cycle = max_cycle;
- }
- return cycle;
- }
- /* API */
- void ppi_config_async_sram(PPI_Type *ppi, uint8_t cs_index, uint8_t cmd_start_index, ppi_async_sram_config_t *config)
- {
- ppi_cs_pin_config_t cs_config;
- ppi_cmd_config_t cmd_config;
- assert(!config->ad_mux_mode && (config->port_size != ppi_port_size_32bits));
- assert(((config->base_address & 0xFFFFF) == 0) && (config->size_in_byte > 0)); /* Addr should be aligned by 1MB */
- /*
- * Pin polarity Config
- */
- if (config->cs_valid_polarity) {
- ppi_config_cs_pin_polarity(ppi, cs_index, ppi_cs_idle_pol_low);
- } else {
- ppi_config_cs_pin_polarity(ppi, cs_index, ppi_cs_idle_pol_high);
- }
- if (config->ad_mux_mode) {
- ppi_set_ctrl_pin_dir(ppi, config->adv_ctrl_pin, ppi_ctrl_pin_dir_output);
- ppi_config_ctrl_pin_polarity(ppi, config->adv_ctrl_pin, ppi_ctrl_pol_low);
- }
- ppi_set_ctrl_pin_dir(ppi, config->rel_ctrl_pin, ppi_ctrl_pin_dir_output);
- ppi_config_ctrl_pin_polarity(ppi, config->rel_ctrl_pin, ppi_ctrl_pol_low);
- ppi_set_ctrl_pin_dir(ppi, config->wel_ctrl_pin, ppi_ctrl_pin_dir_output);
- ppi_config_ctrl_pin_polarity(ppi, config->wel_ctrl_pin, ppi_ctrl_pol_low);
- /*
- * Read Cmd
- */
- /* common */
- cmd_config.cs_pin_value = config->cs_valid_polarity;
- cmd_config.clk_output = false;
- if (config->ad_mux_mode) {
- cmd_config.byte_sel[0] = ppi_byte_sel_0_7_bits;
- cmd_config.byte_sel[1] = ppi_byte_sel_8_15_bits;
- cmd_config.byte_sel[2] = ppi_byte_sel_16_23_bits;
- cmd_config.byte_sel[3] = ppi_byte_sel_24_31_bits;
- } else {
- if (config->port_size == ppi_port_size_8bits) {
- cmd_config.ad_func_sel[0] = ppi_ad_func_data;
- cmd_config.ad_pin_dir[0] = ppi_ad_pin_dir_input;
- cmd_config.byte_sel[0] = ppi_byte_sel_0_7_bits;
- for (uint8_t i = 1; i < 4; i++) {
- cmd_config.ad_func_sel[i] = ppi_ad_func_addr;
- cmd_config.ad_pin_dir[i] = ppi_ad_pin_dir_output;
- }
- cmd_config.byte_sel[1] = ppi_byte_sel_0_7_bits;
- cmd_config.byte_sel[2] = ppi_byte_sel_8_15_bits;
- cmd_config.byte_sel[3] = ppi_byte_sel_16_23_bits;
- } else if (config->port_size == ppi_port_size_16bits) {
- for (uint8_t i = 0; i < 2; i++) {
- cmd_config.ad_func_sel[i] = ppi_ad_func_data;
- cmd_config.ad_pin_dir[i] = ppi_ad_pin_dir_input;
- }
- cmd_config.byte_sel[0] = ppi_byte_sel_0_7_bits;
- cmd_config.byte_sel[1] = ppi_byte_sel_8_15_bits;
- for (uint8_t i = 2; i < 4; i++) {
- cmd_config.ad_func_sel[i] = ppi_ad_func_addr;
- cmd_config.ad_pin_dir[i] = ppi_ad_pin_dir_output;
- }
- cmd_config.byte_sel[2] = ppi_byte_sel_0_7_bits;
- cmd_config.byte_sel[3] = ppi_byte_sel_8_15_bits;
- } else {
- ; /* Not Support */
- }
- }
- cmd_config.ctrl_pin_value[config->wel_ctrl_pin] = true;
- /* AS Stage */
- cmd_config.cmd_cycle = ppi_ns2cycle(config->as_in_ns);
- if (config->ad_mux_mode) {
- for (uint8_t i = 0; i < 4; i++) {
- cmd_config.ad_func_sel[i] = ppi_ad_func_addr;
- cmd_config.ad_pin_dir[i] = ppi_ad_pin_dir_output;
- }
- cmd_config.ctrl_pin_value[config->adv_ctrl_pin] = config->addr_valid_polarity;
- }
- cmd_config.ctrl_pin_value[config->rel_ctrl_pin] = true;
- ppi_config_cmd(ppi, cmd_start_index, &cmd_config);
- /* AH Stage */
- cmd_config.cmd_cycle = ppi_ns2cycle(config->ah_in_ns);
- if (config->ad_mux_mode) {
- for (uint8_t i = 0; i < 4; i++) {
- cmd_config.ad_func_sel[i] = ppi_ad_func_addr;
- cmd_config.ad_pin_dir[i] = ppi_ad_pin_dir_output;
- }
- cmd_config.ctrl_pin_value[config->adv_ctrl_pin] = !config->addr_valid_polarity;
- }
- cmd_config.ctrl_pin_value[config->rel_ctrl_pin] = true;
- ppi_config_cmd(ppi, cmd_start_index + 1, &cmd_config);
- /* REL Stage */
- cmd_config.cmd_cycle = ppi_ns2cycle(config->rel_in_ns);
- if (config->ad_mux_mode) {
- for (uint8_t i = 0; i < 4; i++) {
- cmd_config.ad_func_sel[i] = ppi_ad_func_data;
- cmd_config.ad_pin_dir[i] = ppi_ad_pin_dir_input;
- }
- cmd_config.ctrl_pin_value[config->adv_ctrl_pin] = !config->addr_valid_polarity;
- }
- cmd_config.ctrl_pin_value[config->rel_ctrl_pin] = false;
- ppi_config_cmd(ppi, cmd_start_index + 2, &cmd_config);
- /* REH Stage */
- cmd_config.cmd_cycle = ppi_ns2cycle(config->reh_in_ns);
- if (config->ad_mux_mode) {
- for (uint8_t i = 0; i < 4; i++) {
- cmd_config.ad_func_sel[i] = ppi_ad_func_data;
- cmd_config.ad_pin_dir[i] = ppi_ad_pin_dir_input;
- }
- cmd_config.ctrl_pin_value[config->adv_ctrl_pin] = !config->addr_valid_polarity;
- }
- cmd_config.ctrl_pin_value[config->rel_ctrl_pin] = true;
- ppi_config_cmd(ppi, cmd_start_index + 3, &cmd_config);
- /*
- * Write Cmd
- */
- /* common */
- cmd_config.cs_pin_value = config->cs_valid_polarity;
- cmd_config.clk_output = false;
- if (config->ad_mux_mode) {
- cmd_config.byte_sel[0] = ppi_byte_sel_0_7_bits;
- cmd_config.byte_sel[1] = ppi_byte_sel_8_15_bits;
- cmd_config.byte_sel[2] = ppi_byte_sel_16_23_bits;
- cmd_config.byte_sel[3] = ppi_byte_sel_24_31_bits;
- } else {
- if (config->port_size == ppi_port_size_8bits) {
- cmd_config.ad_func_sel[0] = ppi_ad_func_data;
- cmd_config.ad_pin_dir[0] = ppi_ad_pin_dir_output;
- cmd_config.byte_sel[0] = ppi_byte_sel_0_7_bits;
- for (uint8_t i = 1; i < 4; i++) {
- cmd_config.ad_func_sel[i] = ppi_ad_func_addr;
- cmd_config.ad_pin_dir[i] = ppi_ad_pin_dir_output;
- }
- cmd_config.byte_sel[1] = ppi_byte_sel_0_7_bits;
- cmd_config.byte_sel[2] = ppi_byte_sel_8_15_bits;
- cmd_config.byte_sel[3] = ppi_byte_sel_16_23_bits;
- } else if (config->port_size == ppi_port_size_16bits) {
- for (uint8_t i = 0; i < 2; i++) {
- cmd_config.ad_func_sel[i] = ppi_ad_func_data;
- cmd_config.ad_pin_dir[i] = ppi_ad_pin_dir_output;
- }
- cmd_config.byte_sel[0] = ppi_byte_sel_0_7_bits;
- cmd_config.byte_sel[1] = ppi_byte_sel_8_15_bits;
- for (uint8_t i = 2; i < 4; i++) {
- cmd_config.ad_func_sel[i] = ppi_ad_func_addr;
- cmd_config.ad_pin_dir[i] = ppi_ad_pin_dir_output;
- }
- cmd_config.byte_sel[2] = ppi_byte_sel_0_7_bits;
- cmd_config.byte_sel[3] = ppi_byte_sel_8_15_bits;
- } else {
- ; /* Not Support */
- }
- }
- cmd_config.ctrl_pin_value[config->rel_ctrl_pin] = true;
- /* AS Stage */
- cmd_config.cmd_cycle = ppi_ns2cycle(config->as_in_ns);
- if (config->ad_mux_mode) {
- for (uint8_t i = 0; i < 4; i++) {
- cmd_config.ad_func_sel[i] = ppi_ad_func_addr;
- cmd_config.ad_pin_dir[i] = ppi_ad_pin_dir_output;
- }
- cmd_config.ctrl_pin_value[config->adv_ctrl_pin] = config->addr_valid_polarity;
- }
- cmd_config.ctrl_pin_value[config->wel_ctrl_pin] = true;
- ppi_config_cmd(ppi, cmd_start_index + 4, &cmd_config);
- /* AH Stage */
- cmd_config.cmd_cycle = ppi_ns2cycle(config->ah_in_ns);
- if (config->ad_mux_mode) {
- for (uint8_t i = 0; i < 4; i++) {
- cmd_config.ad_func_sel[i] = ppi_ad_func_addr;
- cmd_config.ad_pin_dir[i] = ppi_ad_pin_dir_output;
- }
- cmd_config.ctrl_pin_value[config->adv_ctrl_pin] = !config->addr_valid_polarity;
- }
- cmd_config.ctrl_pin_value[config->wel_ctrl_pin] = true;
- ppi_config_cmd(ppi, cmd_start_index + 5, &cmd_config);
- /* WEL Stage */
- cmd_config.cmd_cycle = ppi_ns2cycle(config->wel_in_ns);
- if (config->ad_mux_mode) {
- for (uint8_t i = 0; i < 4; i++) {
- cmd_config.ad_func_sel[i] = ppi_ad_func_data;
- cmd_config.ad_pin_dir[i] = ppi_ad_pin_dir_output;
- }
- cmd_config.ctrl_pin_value[config->adv_ctrl_pin] = !config->addr_valid_polarity;
- }
- cmd_config.ctrl_pin_value[config->wel_ctrl_pin] = false;
- ppi_config_cmd(ppi, cmd_start_index + 6, &cmd_config);
- /* WEH Stage */
- cmd_config.cmd_cycle = ppi_ns2cycle(config->weh_in_ns);
- if (config->ad_mux_mode) {
- for (uint8_t i = 0; i < 4; i++) {
- cmd_config.ad_func_sel[i] = ppi_ad_func_data;
- cmd_config.ad_pin_dir[i] = ppi_ad_pin_dir_output;
- }
- cmd_config.ctrl_pin_value[config->adv_ctrl_pin] = !config->addr_valid_polarity;
- }
- cmd_config.ctrl_pin_value[config->wel_ctrl_pin] = true;
- ppi_config_cmd(ppi, cmd_start_index + 7, &cmd_config);
- /*
- * CS Config
- */
- cs_config.addr_start_high_12bits = (config->base_address & 0xFFF00000u) >> 20u;
- cs_config.addr_end_high_12bits = ((config->base_address + (config->size_in_byte - 1u)) & 0xFFF00000u) >> 20u;
- cs_config.port_size = config->port_size;
- cs_config.addr_mask = 0xFFFFu;
- cs_config.sync_clk_en = false;
- cs_config.sync_clk_sel = 0;
- cs_config.interval_cycle = 2;
- cs_config.rcmd_start0 = cmd_start_index;
- cs_config.rcmd_end0 = cmd_start_index + 3;
- cs_config.rcmd_start1 = cmd_start_index;
- cs_config.rcmd_end1 = cmd_start_index + 3;
- cs_config.wcmd_start0 = cmd_start_index + 4;
- cs_config.wcmd_end0 = cmd_start_index + 7;
- cs_config.wcmd_start1 = cmd_start_index + 4;
- cs_config.wcmd_end1 = cmd_start_index + 7;
- #if defined(HPM_IP_FEATURE_PPI_DM_POLARITY_EACH_CS) && HPM_IP_FEATURE_PPI_DM_POLARITY_EACH_CS
- if (config->dm_valid_polarity) {
- cs_config.dm_polarity = ppi_dm_valid_pol_high;
- } else {
- cs_config.dm_polarity = ppi_dm_valid_pol_low;
- }
- #else
- if (config->dm_valid_polarity) {
- ppi_config_dm_pin_polarity(ppi, cs_index, ppi_dm_valid_pol_high);
- } else {
- ppi_config_dm_pin_polarity(ppi, cs_index, ppi_dm_valid_pol_low);
- }
- #endif
- ppi_config_cs_pin(ppi, cs_index, &cs_config);
- }
|