blob: a26f0fcb888d9d84229ba9f7002f68cee09d080e [file] [log] [blame]
// Copyright lowRISC contributors.
// Licensed under the Apache License, Version 2.0, see LICENSE for details.
// SPDX-License-Identifier: Apache-2.0
#include "sw/device/lib/pinmux.h"
#include "sw/device/lib/base/mmio.h"
#include "hw/top_earlgrey/sw/autogen/top_earlgrey.h"
#include "pinmux_regs.h" // Generated.
#define PINMUX0_BASE_ADDR TOP_EARLGREY_PINMUX_AON_BASE_ADDR
// TODO: autogenerated constants for this will be available once
// the pinmux datastructure has been overhauled.
#define NUM_GPIO 32
#define UART_RX_PERIPH_IDX 32
#define UART_TX_PERIPH_IDX 32
#define MIO_32_IOR2_IDX 32
#define MIO_33_IOR3_IDX 33
static void init_pinmux_reg(uint32_t reg, uint32_t mask, uint32_t start_v) {
mmio_region_t reg32 = mmio_region_from_addr(reg);
uint32_t reg_value = start_v;
uint32_t reg_offset = 0;
// We've got 32 GPIOs
for (uint32_t i = 0; i < NUM_GPIO; ++i) {
mmio_region_write32(reg32, reg_offset, reg_value & mask);
reg_value++;
reg_offset += 4;
}
}
void pinmux_init(void) {
// TODO: This hardcoded configuration is temporary and needs to be
// replaced by proper initialization code once 1) the pinmux DIF is
// available, 2) the pinmux and padring design is finalized.
// input: assign MIO0..MIO31 to GPIO0..GPIO31
init_pinmux_reg(PINMUX0_BASE_ADDR + PINMUX_MIO_PERIPH_INSEL_0_REG_OFFSET,
PINMUX_MIO_PERIPH_INSEL_0_IN_0_MASK,
PINMUX_MIO_PERIPH_INSEL_IDX_OFFSET);
// output: assign GPIO0..GPIO31 to MIO0..MIO31
init_pinmux_reg(PINMUX0_BASE_ADDR + PINMUX_MIO_OUTSEL_0_REG_OFFSET,
PINMUX_MIO_OUTSEL_0_OUT_0_MASK,
PINMUX_PERIPH_OUTSEL_IDX_OFFSET);
// Configure UART RX input to connect to MIO pad 32
mmio_region_t reg32 = mmio_region_from_addr(
PINMUX0_BASE_ADDR + PINMUX_MIO_PERIPH_INSEL_0_REG_OFFSET);
uint32_t reg_value = MIO_32_IOR2_IDX + PINMUX_MIO_PERIPH_INSEL_IDX_OFFSET;
uint32_t reg_offset = UART_RX_PERIPH_IDX << 2;
uint32_t mask = PINMUX_MIO_PERIPH_INSEL_0_IN_0_MASK;
mmio_region_write32(reg32, reg_offset, reg_value & mask);
// Configure UART TX output to connect to MIO pad 33
reg32 =
mmio_region_from_addr(PINMUX0_BASE_ADDR + PINMUX_MIO_OUTSEL_0_REG_OFFSET);
reg_value = UART_TX_PERIPH_IDX + PINMUX_PERIPH_OUTSEL_IDX_OFFSET;
reg_offset = MIO_33_IOR3_IDX << 2;
mask = PINMUX_MIO_OUTSEL_0_OUT_0_MASK;
mmio_region_write32(reg32, reg_offset, reg_value & mask);
}