M module-sys/SystemManager/SystemManager.cpp => module-sys/SystemManager/SystemManager.cpp +17 -0
@@ 33,6 33,7 @@
#include <time/ScopedTime.hpp>
#include "Timers/TimerFactory.hpp"
#include <service-appmgr/StartupType.hpp>
+#include <purefs/vfs_subsystem.hpp>
const inline size_t systemManagerStack = 4096 * 2;
@@ 642,6 643,12 @@ namespace sys
deviceManager->RegisterNewDevice(powerManager->getExternalRamDevice());
+ cpuSentinel = std::make_shared<sys::CpuSentinel>(
+ service::name::system_manager, this, [this](bsp::CpuFrequencyHz newFrequency) {
+ UpdateResourcesAfterCpuFrequencyChange(newFrequency);
+ });
+ powerManager->RegisterNewSentinel(cpuSentinel);
+
return ReturnCodes::Success;
}
@@ 773,6 780,16 @@ namespace sys
return MessageNone{};
}
+ void SystemManager::UpdateResourcesAfterCpuFrequencyChange(bsp::CpuFrequencyHz newFrequency)
+ {
+ if (newFrequency == bsp::CpuFrequencyHz::Level_1) {
+ purefs::subsystem::disk_mgr()->pm_control(purefs::blkdev::pm_state::suspend);
+ }
+ else {
+ purefs::subsystem::disk_mgr()->pm_control(purefs::blkdev::pm_state::active);
+ }
+ }
+
std::vector<std::shared_ptr<Service>> SystemManager::servicesList;
std::vector<std::shared_ptr<app::Application>> SystemManager::applicationsList;
cpp_freertos::MutexStandard SystemManager::serviceDestroyMutex;
M module-sys/SystemManager/SystemManager.hpp => module-sys/SystemManager/SystemManager.hpp +5 -0
@@ 189,6 189,9 @@ namespace sys
/// periodic update of cpu statistics
void CpuStatisticsTimerHandler();
+ /// used for power management control for the filesystem
+ void UpdateResourcesAfterCpuFrequencyChange(bsp::CpuFrequencyHz newFrequency);
+
MessagePointer handlePhoneModeRequest(PhoneModeRequest *request);
MessagePointer handleTetheringStateRequest(TetheringStateRequest *request);
MessagePointer enableTethering(TetheringEnabledResponse *response);
@@ 208,6 211,8 @@ namespace sys
InitFunction systemInit;
std::vector<std::string> readyForCloseRegister;
+ std::shared_ptr<sys::CpuSentinel> cpuSentinel;
+
static std::vector<std::shared_ptr<Service>> servicesList;
static std::vector<std::shared_ptr<app::Application>> applicationsList;
static cpp_freertos::MutexStandard serviceDestroyMutex;
M module-vfs/board/linux/purefs/include/purefs/blkdev/disk_image.hpp => module-vfs/board/linux/purefs/include/purefs/blkdev/disk_image.hpp +3 -0
@@ 28,10 28,13 @@ namespace purefs::blkdev
auto status() const -> media_status override;
auto get_info(info_type what, hwpart_t hwpart) const -> scount_t override;
auto erase(sector_t lba, std::size_t count, hwpart_t hwpart) -> int override;
+ auto pm_control(pm_state target_state) -> int override;
+ auto pm_read(pm_state ¤t_state) -> int override;
auto range_valid(sector_t lba, std::size_t count, hwpart_t hwpart) const -> bool;
auto open_and_truncate(hwpart_t hwpart) -> int;
private:
+ pm_state pmState{pm_state::active};
std::vector<int> m_filedes;
std::vector<std::size_t> m_sectors;
const std::string m_image_name;
M module-vfs/board/linux/purefs/src/blkdev/disk_image.cpp => module-vfs/board/linux/purefs/src/blkdev/disk_image.cpp +12 -0
@@ 186,4 186,16 @@ namespace purefs::blkdev
}
return 0;
}
+
+ auto disk_image::pm_control(pm_state target_state) -> int
+ {
+ pmState = target_state;
+ return 0;
+ }
+ auto disk_image::pm_read(pm_state ¤t_state) -> int
+ {
+ current_state = pmState;
+ return 0;
+ }
+
} // namespace purefs::blkdev
M module-vfs/board/rt1051/purefs/include/purefs/blkdev/disk_emmc.hpp => module-vfs/board/rt1051/purefs/include/purefs/blkdev/disk_emmc.hpp +7 -1
@@ 3,6 3,7 @@
#pragma once
+#include "drivers/usdhc/DriverUSDHC.hpp"
#include <purefs/blkdev/disk.hpp>
#include <mutex.hpp>
#include <memory>
@@ 33,14 34,19 @@ namespace purefs::blkdev
auto status() const -> media_status override;
auto get_info(info_type what, hwpart_t hwpart) const -> scount_t override;
auto erase(sector_t lba, std::size_t count, hwpart_t hwpart) -> int override;
+ auto pm_control(pm_state target_state) -> int override;
+ auto pm_read(pm_state ¤t_state) -> int override;
private:
auto switch_partition(hwpart_t newpart) -> int;
private:
int initStatus;
- std::unique_ptr<_mmc_card> mmcCard;
+ pm_state pmState{pm_state::active};
mutable cpp_freertos::MutexRecursive mutex;
std::atomic<hwpart_t> currHwPart{0};
+
+ std::unique_ptr<_mmc_card> mmcCard;
+ std::shared_ptr<drivers::DriverUSDHC> driverUSDHC;
};
} // namespace purefs::blkdev
M module-vfs/board/rt1051/purefs/src/blkdev/disk_emmc.cpp => module-vfs/board/rt1051/purefs/src/blkdev/disk_emmc.cpp +53 -2
@@ 8,6 8,7 @@
#include <bsp/common.hpp>
#include "board/rt1051/bsp/eMMC/fsl_mmc.h"
+#include "bsp/BoardDefinitions.hpp"
namespace purefs::blkdev
{
@@ 21,6 22,9 @@ namespace purefs::blkdev
mmcCard->enablePreDefinedBlockCount = true;
mmcCard->host.base = USDHC2;
mmcCard->host.sourceClock_Hz = GetPerphSourceClock(PerphClock_USDHC2);
+
+ driverUSDHC = drivers::DriverUSDHC::Create(
+ "EMMC", static_cast<drivers::USDHCInstances>(BoardDefinitions::EMMC_USDHC_INSTANCE));
}
disk_emmc::~disk_emmc()
@@ 57,7 61,13 @@ namespace purefs::blkdev
if (err != kStatus_Success) {
return err;
}
+ if (pmState == pm_state::suspend) {
+ driverUSDHC->Enable();
+ }
err = MMC_WriteBlocks(mmcCard.get(), static_cast<const uint8_t *>(buf), lba, count);
+ if (pmState == pm_state::suspend) {
+ driverUSDHC->Disable();
+ }
if (err != kStatus_Success) {
return err;
}
@@ 80,7 90,13 @@ namespace purefs::blkdev
if (err != kStatus_Success) {
return err;
}
+ if (pmState == pm_state::suspend) {
+ driverUSDHC->Enable();
+ }
err = MMC_ReadBlocks(mmcCard.get(), static_cast<uint8_t *>(buf), lba, count);
+ if (pmState == pm_state::suspend) {
+ driverUSDHC->Disable();
+ }
if (err != kStatus_Success) {
return err;
}
@@ 96,8 112,14 @@ namespace purefs::blkdev
while ((GET_SDMMCHOST_STATUS(mmcCard->host.base) & CARD_DATA0_STATUS_MASK) != CARD_DATA0_NOT_BUSY) {
taskYIELD();
}
-
- if (kStatus_Success != MMC_WaitWriteComplete(mmcCard.get())) {
+ if (pmState == pm_state::suspend) {
+ driverUSDHC->Enable();
+ }
+ auto err = MMC_WaitWriteComplete(mmcCard.get());
+ if (pmState == pm_state::suspend) {
+ driverUSDHC->Disable();
+ }
+ if (err != kStatus_Success) {
return kStatus_SDMMC_WaitWriteCompleteFailed;
}
return statusBlkDevSuccess;
@@ 148,7 170,13 @@ namespace purefs::blkdev
}
int ret{};
if (newpart != currHwPart) {
+ if (pmState == pm_state::suspend) {
+ driverUSDHC->Enable();
+ }
ret = MMC_SelectPartition(mmcCard.get(), static_cast<mmc_access_partition_t>(newpart));
+ if (pmState == pm_state::suspend) {
+ driverUSDHC->Disable();
+ }
if (ret == kStatus_Success) {
currHwPart = newpart;
}
@@ 159,4 187,27 @@ namespace purefs::blkdev
return ret;
}
+ auto disk_emmc::pm_control(pm_state target_state) -> int
+ {
+ if (pmState != target_state) {
+ cpp_freertos::LockGuard lock(mutex);
+ if (target_state == pm_state::suspend) {
+ driverUSDHC->Disable();
+ }
+ else {
+ driverUSDHC->Enable();
+ }
+
+ pmState = target_state;
+ }
+
+ return kStatus_Success;
+ }
+
+ auto disk_emmc::pm_read(pm_state ¤t_state) -> int
+ {
+ current_state = pmState;
+ return kStatus_Success;
+ }
+
} // namespace purefs::blkdev
M module-vfs/include/user/purefs/vfs_subsystem.hpp => module-vfs/include/user/purefs/vfs_subsystem.hpp +1 -1
@@ 1,4 1,4 @@
-// Copyright (c) 2017-2020, Mudita Sp. z.o.o. All rights reserved.
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#pragma once