|
|
|
@ -840,6 +840,50 @@ ResultVal<VAddr> PageTable::AllocateAndMapMemory(std::size_t needed_num_pages, s
|
|
|
|
|
return MakeResult<VAddr>(addr);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
ResultCode PageTable::LockForDeviceAddressSpace(VAddr addr, std::size_t size) {
|
|
|
|
|
std::lock_guard lock{page_table_lock};
|
|
|
|
|
|
|
|
|
|
MemoryPermission perm{};
|
|
|
|
|
if (const ResultCode result{CheckMemoryState(
|
|
|
|
|
nullptr, &perm, nullptr, addr, size, MemoryState::FlagCanChangeAttribute,
|
|
|
|
|
MemoryState::FlagCanChangeAttribute, MemoryPermission::None, MemoryPermission::None,
|
|
|
|
|
MemoryAttribute::LockedAndIpcLocked, MemoryAttribute::None,
|
|
|
|
|
MemoryAttribute::DeviceSharedAndUncached)};
|
|
|
|
|
result.IsError()) {
|
|
|
|
|
return result;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
block_manager->UpdateLock(addr, size / PageSize,
|
|
|
|
|
[perm](MemoryBlockManager::iterator block, MemoryPermission perm) {
|
|
|
|
|
block->ShareToDevice(perm);
|
|
|
|
|
},
|
|
|
|
|
perm);
|
|
|
|
|
|
|
|
|
|
return RESULT_SUCCESS;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
ResultCode PageTable::UnlockForDeviceAddressSpace(VAddr addr, std::size_t size) {
|
|
|
|
|
std::lock_guard lock{page_table_lock};
|
|
|
|
|
|
|
|
|
|
MemoryPermission perm{};
|
|
|
|
|
if (const ResultCode result{CheckMemoryState(
|
|
|
|
|
nullptr, &perm, nullptr, addr, size, MemoryState::FlagCanChangeAttribute,
|
|
|
|
|
MemoryState::FlagCanChangeAttribute, MemoryPermission::None, MemoryPermission::None,
|
|
|
|
|
MemoryAttribute::LockedAndIpcLocked, MemoryAttribute::None,
|
|
|
|
|
MemoryAttribute::DeviceSharedAndUncached)};
|
|
|
|
|
result.IsError()) {
|
|
|
|
|
return result;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
block_manager->UpdateLock(addr, size / PageSize,
|
|
|
|
|
[perm](MemoryBlockManager::iterator block, MemoryPermission perm) {
|
|
|
|
|
block->UnshareToDevice(perm);
|
|
|
|
|
},
|
|
|
|
|
perm);
|
|
|
|
|
|
|
|
|
|
return RESULT_SUCCESS;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
ResultCode PageTable::InitializeMemoryLayout(VAddr start, VAddr end) {
|
|
|
|
|
block_manager = std::make_unique<MemoryBlockManager>(start, end);
|
|
|
|
|
|
|
|
|
|