mirror of
https://github.com/zephyrproject-rtos/zephyr
synced 2025-09-04 03:11:58 +00:00
UARTs and I2C controllers are accessed through MMIO and these regions need to be added to MMU for proper access. This also enable MMU for Apollo Lake by default since serial console is now usable. Signed-off-by: Daniel Leung <daniel.leung@intel.com>
226 lines
7.1 KiB
C
226 lines
7.1 KiB
C
/*
|
|
* Copyright (c) 2018, Intel Corporation
|
|
* Copyright (c) 2011-2015, Wind River Systems, Inc.
|
|
*
|
|
* SPDX-License-Identifier: Apache-2.0
|
|
*/
|
|
|
|
/**
|
|
* @file
|
|
* @brief System/hardware module for the Apollo Lake SoC
|
|
*
|
|
* This module provides routines to initialize and support soc-level hardware
|
|
* for the Apollo Lake SoC.
|
|
*/
|
|
|
|
#include <kernel.h>
|
|
#include "soc.h"
|
|
#include <drivers/uart.h>
|
|
#include <device.h>
|
|
#include <init.h>
|
|
|
|
#ifdef CONFIG_PCIE
|
|
#include <drivers/pcie/pcie.h>
|
|
#endif
|
|
|
|
#ifdef CONFIG_X86_MMU
|
|
/* loapic */
|
|
MMU_BOOT_REGION(CONFIG_LOAPIC_BASE_ADDRESS, 4 * 1024, MMU_ENTRY_WRITE);
|
|
|
|
/* ioapic */
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_INST(0, intel_ioapic)), 1024 * 1024, MMU_ENTRY_WRITE);
|
|
|
|
#ifdef CONFIG_HPET_TIMER
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_INST(0, intel_hpet)), KB(4), MMU_ENTRY_WRITE);
|
|
#endif /* CONFIG_HPET_TIMER */
|
|
|
|
/* for UARTs */
|
|
#if DT_NODE_HAS_STATUS(DT_INST(0, ns16550), okay) && \
|
|
!DT_PROP(DT_INST(0, ns16550), pcie)
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_INST(0, ns16550)), 0x1000,
|
|
(MMU_ENTRY_READ | MMU_ENTRY_WRITE));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(1, ns16550), okay) && \
|
|
!DT_PROP(DT_INST(1, ns16550), pcie)
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_INST(1, ns16550)), 0x1000,
|
|
(MMU_ENTRY_READ | MMU_ENTRY_WRITE));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(2, ns16550), okay) && \
|
|
!DT_PROP(DT_INST(2, ns16550), pcie)
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_INST(2, ns16550)), 0x1000,
|
|
(MMU_ENTRY_READ | MMU_ENTRY_WRITE));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(3, ns16550), okay) && \
|
|
!DT_PROP(DT_INST(3, ns16550), pcie)
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_INST(3, ns16550)), 0x1000,
|
|
(MMU_ENTRY_READ | MMU_ENTRY_WRITE));
|
|
#endif
|
|
|
|
/* for I2C controllers */
|
|
#ifdef CONFIG_I2C
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(0, snps_designware_i2c), okay) && \
|
|
!DT_PROP(DT_INST(0, snps_designware_i2c), pcie)
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_INST(0, snps_designware_i2c)), 0x1000,
|
|
(MMU_ENTRY_READ | MMU_ENTRY_WRITE));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(1, snps_designware_i2c), okay) && \
|
|
!DT_PROP(DT_INST(1, snps_designware_i2c), pcie)
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_INST(1, snps_designware_i2c)), 0x1000,
|
|
(MMU_ENTRY_READ | MMU_ENTRY_WRITE));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(2, snps_designware_i2c), okay) && \
|
|
!DT_PROP(DT_INST(2, snps_designware_i2c), pcie)
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_INST(2, snps_designware_i2c)), 0x1000,
|
|
(MMU_ENTRY_READ | MMU_ENTRY_WRITE));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(3, snps_designware_i2c), okay) && \
|
|
!DT_PROP(DT_INST(3, snps_designware_i2c), pcie)
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_INST(3, snps_designware_i2c)), 0x1000,
|
|
(MMU_ENTRY_READ | MMU_ENTRY_WRITE));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(4, snps_designware_i2c), okay) && \
|
|
!DT_PROP(DT_INST(4, snps_designware_i2c), pcie)
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_INST(4, snps_designware_i2c)), 0x1000,
|
|
(MMU_ENTRY_READ | MMU_ENTRY_WRITE));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(5, snps_designware_i2c), okay) && \
|
|
!DT_PROP(DT_INST(5, snps_designware_i2c), pcie)
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_INST(5, snps_designware_i2c)), 0x1000,
|
|
(MMU_ENTRY_READ | MMU_ENTRY_WRITE));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(6, snps_designware_i2c), okay) && \
|
|
!DT_PROP(DT_INST(6, snps_designware_i2c), pcie)
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_INST(6, snps_designware_i2c)), 0x1000,
|
|
(MMU_ENTRY_READ | MMU_ENTRY_WRITE));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(7, snps_designware_i2c), okay) && \
|
|
!DT_PROP(DT_INST(7, snps_designware_i2c), pcie)
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_INST(7, snps_designware_i2c)), 0x1000,
|
|
(MMU_ENTRY_READ | MMU_ENTRY_WRITE));
|
|
#endif
|
|
|
|
#endif /* CONFIG_I2C */
|
|
|
|
/* for GPIO controller */
|
|
#ifdef CONFIG_GPIO_INTEL_APL
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_NODELABEL(gpio_n_000_031)),
|
|
DT_REG_SIZE(DT_NODELABEL(gpio_n_000_031)),
|
|
(MMU_ENTRY_READ | MMU_ENTRY_WRITE));
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_NODELABEL(gpio_nw_000_031)),
|
|
DT_REG_SIZE(DT_NODELABEL(gpio_nw_000_031)),
|
|
(MMU_ENTRY_READ | MMU_ENTRY_WRITE));
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_NODELABEL(gpio_w_000_031)),
|
|
DT_REG_SIZE(DT_NODELABEL(gpio_w_000_031)),
|
|
(MMU_ENTRY_READ | MMU_ENTRY_WRITE));
|
|
MMU_BOOT_REGION(DT_REG_ADDR(DT_NODELABEL(gpio_sw_000_031)),
|
|
DT_REG_SIZE(DT_NODELABEL(gpio_sw_000_031)),
|
|
(MMU_ENTRY_READ | MMU_ENTRY_WRITE));
|
|
#endif
|
|
|
|
static void device_mmu_region(pcie_bdf_t bdf, pcie_id_t id)
|
|
{
|
|
mm_reg_t base;
|
|
|
|
if (pcie_probe(bdf, id)) {
|
|
base = pcie_get_mbar(bdf, 0);
|
|
|
|
if (base != PCIE_CONF_BAR_NONE) {
|
|
z_x86_add_mmu_region(
|
|
base, 0x1000,
|
|
MMU_ENTRY_READ | MMU_ENTRY_WRITE);
|
|
}
|
|
}
|
|
}
|
|
|
|
void z_x86_soc_add_mmu_regions(void)
|
|
{
|
|
#ifdef CONFIG_PCIE
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(0, ns16550), okay) && \
|
|
DT_PROP(DT_INST(0, ns16550), pcie)
|
|
device_mmu_region(DT_REG_ADDR(DT_INST(0, ns16550)),
|
|
DT_REG_SIZE(DT_INST(0, ns16550)));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(1, ns16550), okay) && \
|
|
DT_PROP(DT_INST(1, ns16550), pcie)
|
|
device_mmu_region(DT_REG_ADDR(DT_INST(1, ns16550)),
|
|
DT_REG_SIZE(DT_INST(1, ns16550)));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(2, ns16550), okay) && \
|
|
DT_PROP(DT_INST(2, ns16550), pcie)
|
|
device_mmu_region(DT_REG_ADDR(DT_INST(2, ns16550)),
|
|
DT_REG_SIZE(DT_INST(2, ns16550)));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(3, ns16550), okay) && \
|
|
DT_PROP(DT_INST(3, ns16550), pcie)
|
|
device_mmu_region(DT_REG_ADDR(DT_INST(3, ns16550)),
|
|
DT_REG_SIZE(DT_INST(3, ns16550)));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(0, snps_designware_i2c), okay) && \
|
|
DT_PROP(DT_INST(0, snps_designware_i2c), pcie)
|
|
device_mmu_region(DT_REG_ADDR(DT_INST(0, snps_designware_i2c)),
|
|
DT_REG_SIZE(DT_INST(0, snps_designware_i2c)));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(1, snps_designware_i2c), okay) && \
|
|
DT_PROP(DT_INST(1, snps_designware_i2c), pcie)
|
|
device_mmu_region(DT_REG_ADDR(DT_INST(1, snps_designware_i2c)),
|
|
DT_REG_SIZE(DT_INST(1, snps_designware_i2c)));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(2, snps_designware_i2c), okay) && \
|
|
DT_PROP(DT_INST(2, snps_designware_i2c), pcie)
|
|
device_mmu_region(DT_REG_ADDR(DT_INST(2, snps_designware_i2c)),
|
|
DT_REG_SIZE(DT_INST(2, snps_designware_i2c)));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(3, snps_designware_i2c), okay) && \
|
|
DT_PROP(DT_INST(3, snps_designware_i2c), pcie)
|
|
device_mmu_region(DT_REG_ADDR(DT_INST(3, snps_designware_i2c)),
|
|
DT_REG_SIZE(DT_INST(3, snps_designware_i2c)));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(4, snps_designware_i2c), okay) && \
|
|
DT_PROP(DT_INST(4, snps_designware_i2c), pcie)
|
|
device_mmu_region(DT_REG_ADDR(DT_INST(4, snps_designware_i2c)),
|
|
DT_REG_SIZE(DT_INST(4, snps_designware_i2c)));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(5, snps_designware_i2c), okay) && \
|
|
DT_PROP(DT_INST(5, snps_designware_i2c), pcie)
|
|
device_mmu_region(DT_REG_ADDR(DT_INST(5, snps_designware_i2c)),
|
|
DT_REG_SIZE(DT_INST(5, snps_designware_i2c)));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(6, snps_designware_i2c), okay) && \
|
|
DT_PROP(DT_INST(6, snps_designware_i2c), pcie)
|
|
device_mmu_region(DT_REG_ADDR(DT_INST(6, snps_designware_i2c)),
|
|
DT_REG_SIZE(DT_INST(6, snps_designware_i2c)));
|
|
#endif
|
|
|
|
#if DT_NODE_HAS_STATUS(DT_INST(7, snps_designware_i2c), okay) && \
|
|
DT_PROP(DT_INST(7, snps_designware_i2c), pcie)
|
|
device_mmu_region(DT_REG_ADDR(DT_INST(7, snps_designware_i2c)),
|
|
DT_REG_SIZE(DT_INST(7, snps_designware_i2c)));
|
|
#endif
|
|
|
|
#endif /* CONFIG_PCIE */
|
|
}
|
|
|
|
#endif /* CONFIG_X86_MMU */
|