AuroraRuntime/Source/Memory/AuMemorySwapLock.cpp

103 lines
2.7 KiB
C++
Raw Normal View History

/***
Copyright (C) 2022 J Reece Wilson (a/k/a "Reece"). All rights reserved.
2024-03-19 15:47:42 +00:00
File: AuMemorySwapLock.cpp
Date: 2022-3-21
Author: Reece
***/
#include <Source/RuntimeInternal.hpp>
2024-03-19 15:47:42 +00:00
#include "AuMemory.hpp"
#include "AuMemorySwapLock.hpp"
2022-11-17 07:46:07 +00:00
#include <Source/HWInfo/AuHWInfo.hpp>
namespace Aurora::Memory::SwapLock
{
2024-04-09 21:29:11 +00:00
static AuPair<AuUInt, AuUInt> ToPagePair(AuPair<AuUInt, AuUInt> addressRange)
{
auto uBase = AuPageRound(addressRange.first, AuUInt(AuHwInfo::gPageSize));
auto uLength = AuPageRoundUp(addressRange.second + (addressRange.first - uBase), AuUInt(AuHwInfo::gPageSize));
return AuMakePair(uBase, uLength);
}
AUKN_SYM bool Lock(const AuList<AuPair<AuUInt, AuUInt>> &addressRanges)
{
2024-04-09 21:29:11 +00:00
for (AU_ITERATE_N(i, addressRanges.size()))
{
2024-04-09 21:29:11 +00:00
bool bBypass {};
AuUInt uBase, uLength;
AuTupleTie(uBase, uLength) = ToPagePair(addressRanges[i]);
2024-04-09 21:29:11 +00:00
for (AU_ITERATE_N(z, i))
{
2024-04-09 21:29:11 +00:00
AuUInt uBase2, uLength2;
AuTupleTie(uBase2, uLength2) = ToPagePair(addressRanges[z]);
if (uBase < uBase2)
{
continue;
}
if ((uBase + uLength) > (uBase2 + uLength2))
{
continue;
}
bBypass = true;
break;
}
2024-04-09 21:29:11 +00:00
if (!bBypass &&
!SysMemoryLockPages(AuReinterpretCast<const void *>(uBase), uLength))
{
2024-04-09 21:29:11 +00:00
SysPushErrorHAL("Couldn't lock memory 0x{:x} {}", uBase, uLength);
return false;
}
}
return true;
}
AUKN_SYM bool Unlock(const AuList<AuPair<AuUInt, AuUInt>> &addressRanges)
{
2024-04-09 21:29:11 +00:00
bool bRet { true };
for (AU_ITERATE_N(i, addressRanges.size()))
{
2024-04-09 21:29:11 +00:00
bool bBypass {};
AuUInt uBase, uLength;
2024-04-09 21:29:11 +00:00
AuTupleTie(uBase, uLength) = ToPagePair(addressRanges[i]);
for (AU_ITERATE_N(z, i))
{
2024-04-09 21:29:11 +00:00
AuUInt uBase2, uLength2;
AuTupleTie(uBase2, uLength2) = ToPagePair(addressRanges[z]);
if (uBase < uBase2)
{
continue;
}
if ((uBase + uLength) > (uBase2 + uLength2))
{
continue;
}
bBypass = true;
break;
}
2024-04-09 21:29:11 +00:00
if (!bBypass &&
!SysMemoryUnlockPages(AuReinterpretCast<const void *>(uBase), uLength))
{
2024-04-09 21:29:11 +00:00
SysPushErrorHAL("Couldn't unlock memory 0x{:x} {}", uBase, uLength);
bRet = false;
}
}
2024-04-09 21:29:11 +00:00
return bRet;
}
}