Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Bug]: DXE core memory protection feature might cause inconsistency between GCD internal data structure with CPU page table #10771

Open
2 of 5 tasks
qhuang8 opened this issue Feb 19, 2025 · 6 comments
Assignees
Labels
package:mdemodulepkg priority:high Significant impact. Should be fixed as soon as possible. state:needs-triage type:bug Something isn't working

Comments

@qhuang8
Copy link
Contributor

qhuang8 commented Feb 19, 2025

Is there an existing issue for this?

  • I have searched existing issues

Bug Type

  • Firmware
  • Tool
  • Unit Test

Code first?

  • Yes

What packages are impacted?

MdeModulePkg

Which targets are impacted by this bug?

DEBUG, RELEASE

Current Behavior

When we enable DXE core memory protection feature, if we set some GCD irrelevent attributes like EFI_MEMORY_SP or EFI_MEMORY_CPU_CRYPTO via GCD SetMemorySpaceAttributes (), it will cause page fault except.

Expected Behavior

We can still invoke SetMemorySpaceAttributes () successfully to append EFI_MEMORY_SP or EFI_MEMORY_CPU_CRYPTO

Steps To Reproduce

  1. Set the following two platform PCD to enable memory protection.
    PcdSetNxForStack| TRUE
    PcdDxeNxMemoryProtectionPolicy| 0x7FD5

  2. Invoke GCD SetMemorySpaceAttributes () API in later DXE phase to append EFI_MEMORY_SP or EFI_MEMORY_CPU_CRYPTO (keep the original attributes)

  3. System will have page fault exception

Build Environment

- OS(s):Windows 11
- Tool Chain(s): VS2019

Version Information

Commit: f979f51157c5560c658537ea2a488b7a8439e463

Urgency

High

Are you going to fix this?

Someone else needs to fix it

Do you need maintainer feedback?

No maintainer feedback needed

Anything else?

The root cause of this issue is that Edk2\MdeModulePkg\Core\Dxe\Misc\MemoryProtection.c (line 1294) directly uses CPU arch protocol to clear XP in page table when loading DXE driver for execution, but it fails to update the GCD internal data structure according (the memory range still makes as XP attribute):
gCpu->SetMemoryAttributes (gCpu, Memory, Length, NewAttributes);

Later invoking of GCD SetMemorySpaceAttributes () will incorrectly re-apply the incorrect XP attribute and make it take effect in the final page table. When CPU executes the memory, it triggers the page fault exception.

@qhuang8 qhuang8 added state:needs-triage type:bug Something isn't working labels Feb 19, 2025
@github-actions github-actions bot added priority:high Significant impact. Should be fixed as soon as possible. package:mdemodulepkg state:needs-owner labels Feb 19, 2025
@makubacki
Copy link
Member

@os-d, you've looked at this recently. Would you like to follow up?

@os-d os-d self-assigned this Feb 24, 2025
@os-d
Copy link
Contributor

os-d commented Feb 24, 2025

I agree this looks like a correct analysis of the bug. I can take a look at this when I get a chance. In general, the GCD gets very out of sync with the page table, leading to issues like this. I have a lot of fixes and design changes to upstream that fix a number of these issues that I will be working to upstream now that the hard freeze is lifted.

@os-d
Copy link
Contributor

os-d commented Feb 24, 2025

@qhuang8 I was actually unable to repro this on OVMF IA32X64. I updated the PlatformDxe driver to add EFI_MEMORY_SP to the region of CpuDxe covering the CpuSetMemoryAttributes function and keep the other GCD attributes. However, the GCD correctly showed this page was mapped EFI_MEMORY_RO and the driver was able to set SP and CpuDxe could continue to execute.

Can you share a repro on OVMF or ArmVirtPkg? Or a bit more clearly describe the chain of calls you believe is the issue (the line number you cite doesn't exist in that file, I'm guessing you mean 1109?

@qhuang8
Copy link
Contributor Author

qhuang8 commented Feb 25, 2025

Sorry that I am not familiar with OVMF or ArmVirtPkg...

Our use case of GCD SetMemoryAttribute happens in very later DXE phase. We set EFI_MEMORY_CPU_CRYPTO to all availabe DDR memory after PCI enumeration has completed. Before that, I see DXE core has updated CPU page table to drop XP attribute for some code region, but the correspondent GCD internal data structure has not been updated.

@os-d
Copy link
Contributor

os-d commented Feb 25, 2025

@qhuang8 can you share what driver corresponds to that code region? Like I said, when I tried updating a code region of CpuDxe, it had the correct attributes set in the GCD. Perhaps your case is a driver loaded earlier? Or DXE Core itself? I can update my repro attempt accordingly.

@qhuang8
Copy link
Contributor Author

qhuang8 commented Feb 26, 2025

In my platform it is Edk2\NetworkPkg\DnsDxe\DnsDxe.inf driver.

After this driver is loaded, its memory attributes in cpu page table has been changed to drop XP

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
package:mdemodulepkg priority:high Significant impact. Should be fixed as soon as possible. state:needs-triage type:bug Something isn't working
Projects
None yet
Development

No branches or pull requests

3 participants