mirror of
https://github.com/Atmosphere-NX/Atmosphere
synced 2024-11-09 22:56:35 +00:00
kern: finish 1.x lps driver
This commit is contained in:
parent
ab2568ddfb
commit
34dc062c11
7 changed files with 96 additions and 30 deletions
|
@ -17,31 +17,31 @@
|
|||
#include <mesosphere.hpp>
|
||||
|
||||
/* Message Flags */
|
||||
#define BPMP_MSG_DO_ACK (1 << 0)
|
||||
#define BPMP_MSG_DO_ACK (1 << 0)
|
||||
#define BPMP_MSG_RING_DOORBELL (1 << 1)
|
||||
|
||||
/* Messages */
|
||||
#define MRQ_PING 0
|
||||
#define MRQ_ENABLE_SUSPEND 17
|
||||
#define MRQ_PING 0
|
||||
#define MRQ_ENABLE_SUSPEND 17
|
||||
#define MRQ_CPU_PMIC_SELECT 28
|
||||
|
||||
/* BPMP Power states. */
|
||||
#define TEGRA_BPMP_PM_CC1 9
|
||||
#define TEGRA_BPMP_PM_CC4 12
|
||||
#define TEGRA_BPMP_PM_CC6 14
|
||||
#define TEGRA_BPMP_PM_CC7 15
|
||||
#define TEGRA_BPMP_PM_SC1 17
|
||||
#define TEGRA_BPMP_PM_SC2 18
|
||||
#define TEGRA_BPMP_PM_SC3 19
|
||||
#define TEGRA_BPMP_PM_SC4 20
|
||||
#define TEGRA_BPMP_PM_SC7 23
|
||||
#define TEGRA_BPMP_PM_CC1 9
|
||||
#define TEGRA_BPMP_PM_CC4 12
|
||||
#define TEGRA_BPMP_PM_CC6 14
|
||||
#define TEGRA_BPMP_PM_CC7 15
|
||||
#define TEGRA_BPMP_PM_SC1 17
|
||||
#define TEGRA_BPMP_PM_SC2 18
|
||||
#define TEGRA_BPMP_PM_SC3 19
|
||||
#define TEGRA_BPMP_PM_SC4 20
|
||||
#define TEGRA_BPMP_PM_SC7 23
|
||||
|
||||
/* Channel states. */
|
||||
#define CH_MASK(ch) (0x3u << ((ch) * 2))
|
||||
#define SL_SIGL(ch) (0x0u << ((ch) * 2))
|
||||
#define SL_QUED(ch) (0x1u << ((ch) * 2))
|
||||
#define MA_FREE(ch) (0x2u << ((ch) * 2))
|
||||
#define MA_ACKD(ch) (0x3u << ((ch) * 2))
|
||||
#define CH_MASK(ch) (0x3u << ((ch) * 2))
|
||||
#define SL_SIGL(ch) (0x0u << ((ch) * 2))
|
||||
#define SL_QUED(ch) (0x1u << ((ch) * 2))
|
||||
#define MA_FREE(ch) (0x2u << ((ch) * 2))
|
||||
#define MA_ACKD(ch) (0x3u << ((ch) * 2))
|
||||
|
||||
constexpr inline int MessageSize = 0x80;
|
||||
constexpr inline int MessageDataSizeMax = 0x78;
|
||||
|
|
|
@ -0,0 +1,18 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020 Atmosphère-NX
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify it
|
||||
* under the terms and conditions of the GNU General Public License
|
||||
* version 2, as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
|
||||
* more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#define CLK_RST_CONTROLLER_CLK_SOURCE_CSITE 0x1D4
|
|
@ -15,11 +15,11 @@
|
|||
*/
|
||||
#pragma once
|
||||
|
||||
#define ICTLR_REG_BASE(irq) ((((irq) - 32) >> 5) * 0x100)
|
||||
#define ICTLR_FIR_SET(irq) (ICTLR_REG_BASE(irq) + 0x18)
|
||||
#define ICTLR_FIR_CLR(irq) (ICTLR_REG_BASE(irq) + 0x1c)
|
||||
#define FIR_BIT(irq) (1 << ((irq) & 0x1f))
|
||||
#define ICTLR_REG_BASE(irq) ((((irq) - 32) >> 5) * 0x100)
|
||||
#define ICTLR_FIR_SET(irq) (ICTLR_REG_BASE(irq) + 0x18)
|
||||
#define ICTLR_FIR_CLR(irq) (ICTLR_REG_BASE(irq) + 0x1c)
|
||||
#define FIR_BIT(irq) (1 << ((irq) & 0x1f))
|
||||
|
||||
#define INT_GIC_BASE (0)
|
||||
#define INT_PRI_BASE (INT_GIC_BASE + 32)
|
||||
#define INT_GIC_BASE (0)
|
||||
#define INT_PRI_BASE (INT_GIC_BASE + 32)
|
||||
#define INT_SHR_SEM_OUTBOX_IBF (INT_PRI_BASE + 6)
|
||||
|
|
|
@ -561,7 +561,7 @@ namespace ams::kern::board::nintendo::nx {
|
|||
|
||||
/* If we're using the legacy lps driver, enable suspend. */
|
||||
if (use_legacy_lps_driver) {
|
||||
MESOSPHERE_R_ABORT_UNLESS(lps::EnableSuspend());
|
||||
MESOSPHERE_R_ABORT_UNLESS(lps::EnableSuspend(true));
|
||||
}
|
||||
|
||||
/* Log that we're about to enter SC7. */
|
||||
|
|
|
@ -19,8 +19,10 @@
|
|||
|
||||
#include "kern_bpmp_api.hpp"
|
||||
#include "kern_atomics_registers.hpp"
|
||||
#include "kern_ictlr_registers.hpp"
|
||||
#include "kern_clkrst_registers.hpp"
|
||||
#include "kern_flow_registers.hpp"
|
||||
#include "kern_ictlr_registers.hpp"
|
||||
#include "kern_pmc_registers.hpp"
|
||||
#include "kern_sema_registers.hpp"
|
||||
|
||||
namespace ams::kern::board::nintendo::nx::lps {
|
||||
|
@ -43,9 +45,12 @@ namespace ams::kern::board::nintendo::nx::lps {
|
|||
constinit KVirtualAddress g_sema_address = Null<KVirtualAddress>;
|
||||
constinit KVirtualAddress g_atomics_address = Null<KVirtualAddress>;
|
||||
constinit KVirtualAddress g_clkrst_address = Null<KVirtualAddress>;
|
||||
constinit KVirtualAddress g_pmc_address = Null<KVirtualAddress>;
|
||||
|
||||
constinit ChannelData g_channel_area[ChannelCount] = {};
|
||||
|
||||
constinit u32 g_csite_clk_source = 0;
|
||||
|
||||
ALWAYS_INLINE u32 Read(KVirtualAddress address) {
|
||||
return *GetPointer<volatile u32>(address);
|
||||
}
|
||||
|
@ -62,6 +67,7 @@ namespace ams::kern::board::nintendo::nx::lps {
|
|||
g_sema_address = KMemoryLayout::GetDeviceVirtualAddress(KMemoryRegionType_LegacyLpsSemaphore);
|
||||
g_atomics_address = KMemoryLayout::GetDeviceVirtualAddress(KMemoryRegionType_LegacyLpsAtomics);
|
||||
g_clkrst_address = KMemoryLayout::GetDeviceVirtualAddress(KMemoryRegionType_LegacyLpsClkRst);
|
||||
g_pmc_address = KMemoryLayout::GetDeviceVirtualAddress(KMemoryRegionType_PowerManagementController);
|
||||
}
|
||||
|
||||
/* NOTE: linux "do_cc4_init" */
|
||||
|
@ -393,15 +399,36 @@ namespace ams::kern::board::nintendo::nx::lps {
|
|||
}
|
||||
|
||||
void InvokeCpuSleepHandler(uintptr_t arg, uintptr_t entry) {
|
||||
/* Verify that we're allowed to perform suspension. */
|
||||
MESOSPHERE_ABORT_UNLESS(g_lps_init_done);
|
||||
MESOSPHERE_ABORT_UNLESS(GetCurrentCoreId() == 0);
|
||||
|
||||
MESOSPHERE_UNIMPLEMENTED();
|
||||
/* Save the CSITE clock source. */
|
||||
g_csite_clk_source = Read(g_clkrst_address + CLK_RST_CONTROLLER_CLK_SOURCE_CSITE);
|
||||
|
||||
/* Configure CSITE clock source as CLK_M. */
|
||||
Write(g_clkrst_address + CLK_RST_CONTROLLER_CLK_SOURCE_CSITE, (0x6 << 29));
|
||||
|
||||
/* Clear the top bit of PMC_SCRATCH4. */
|
||||
Write(g_pmc_address + APBDEV_PMC_SCRATCH4, Read(g_pmc_address + APBDEV_PMC_SCRATCH4) & 0x7FFFFFFF);
|
||||
|
||||
/* Write 1 to PMC_SCRATCH0. This will cause the bootrom to use the warmboot code-path. */
|
||||
Write(g_pmc_address + APBDEV_PMC_SCRATCH0, 1);
|
||||
|
||||
/* Read PMC_SCRATCH0 to be sure our write takes. */
|
||||
Read(g_pmc_address + APBDEV_PMC_SCRATCH0);
|
||||
|
||||
/* Invoke the sleep hander. */
|
||||
KSleepManager::CpuSleepHandler(arg, entry);
|
||||
|
||||
/* TODO: restore saved clkrst reg */
|
||||
/* Disable deep power down. */
|
||||
Write(g_pmc_address + APBDEV_PMC_DPD_ENABLE, 0);
|
||||
|
||||
/* Restore the saved CSITE clock source. */
|
||||
Write(g_clkrst_address + CLK_RST_CONTROLLER_CLK_SOURCE_CSITE, g_csite_clk_source);
|
||||
|
||||
/* Read the CSITE clock source to ensure our configuration takes. */
|
||||
Read(g_clkrst_address + CLK_RST_CONTROLLER_CLK_SOURCE_CSITE);
|
||||
|
||||
/* Configure CC3/CC4. */
|
||||
ConfigureCc3AndCc4();
|
||||
|
|
|
@ -0,0 +1,20 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020 Atmosphère-NX
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify it
|
||||
* under the terms and conditions of the GNU General Public License
|
||||
* version 2, as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
|
||||
* more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#define APBDEV_PMC_DPD_ENABLE 0x024
|
||||
#define APBDEV_PMC_SCRATCH0 0x050
|
||||
#define APBDEV_PMC_SCRATCH4 0x060
|
|
@ -41,10 +41,11 @@ namespace ams::kern {
|
|||
|
||||
ALWAYS_INLINE bool SetupPowerManagementControllerMemoryRegion() {
|
||||
/* For backwards compatibility, the PMC must remain mappable on < 2.0.0. */
|
||||
const auto restrict_attr = GetTargetFirmware() >= TargetFirmware_2_0_0 ? KMemoryRegionAttr_NoUserMap : static_cast<KMemoryRegionAttr>(0);
|
||||
const auto rtc_restrict_attr = GetTargetFirmware() >= TargetFirmware_2_0_0 ? KMemoryRegionAttr_NoUserMap : static_cast<KMemoryRegionAttr>(0);
|
||||
const auto pmc_restrict_attr = GetTargetFirmware() >= TargetFirmware_2_0_0 ? KMemoryRegionAttr_NoUserMap : KMemoryRegionAttr_ShouldKernelMap;
|
||||
|
||||
return KMemoryLayout::GetPhysicalMemoryRegionTree().Insert(0x7000E000, 0x400, KMemoryRegionType_None | restrict_attr) &&
|
||||
KMemoryLayout::GetPhysicalMemoryRegionTree().Insert(0x7000E400, 0xC00, KMemoryRegionType_PowerManagementController | restrict_attr);
|
||||
return KMemoryLayout::GetPhysicalMemoryRegionTree().Insert(0x7000E000, 0x400, KMemoryRegionType_None | rtc_restrict_attr) &&
|
||||
KMemoryLayout::GetPhysicalMemoryRegionTree().Insert(0x7000E400, 0xC00, KMemoryRegionType_PowerManagementController | pmc_restrict_attr);
|
||||
}
|
||||
|
||||
void InsertPoolPartitionRegionIntoBothTrees(size_t start, size_t size, KMemoryRegionType phys_type, KMemoryRegionType virt_type, u32 &cur_attr) {
|
||||
|
|
Loading…
Reference in a new issue