diff mbox

[v4,0/3] Full PAM emulation (RE^WE) for i440FX and Q35

Message ID 20220630005058.500449-1-lkujaw@member.fsf.org (mailing list archive)
State New, archived
Headers show

Commit Message

Lev Kujawski June 30, 2022, 12:50 a.m. UTC
Hello,

This patch series (v4) implements full PAM emulation for the i440FX
and Q35 x86 platforms (see commit log for details.)  Prior versions
did not support executing code from ROMs within the ISA MMIO range
when mode 2 was active (PAM_WE), but this series adds the requisite
support for new romd_mode memory sections to the QEMU MMU.  It appears
to be working well on TCG and KVM, but I would appreciate any feedback
or testing on other accelerators.  For testing purposes, I have
attached a patch to SeaBIOS that removes its special handling for
QEMU, but unaltered versions run fine as well.

Kind regards,
Lev Kujawski

  hw/pci-host/pam.c: Fully support RE^WE semantics of i440FX PAM
  tests/data/acpi/q35/SSDT.dimmpxm: Account for new E820 entry
  tests/qtest/i440fx-test.c: Enable full test of i440FX PAM operation

 accel/kvm/kvm-all.c              |   2 +-
 accel/tcg/cputlb.c               |  14 ++-
 hw/i386/pc.c                     |  19 ++-
 hw/pci-host/i440fx.c             |  34 +++---
 hw/pci-host/pam.c                | 193 ++++++++++++++++++++++++++-----
 hw/pci-host/q35.c                |  50 ++++----
 include/exec/memory.h            |  19 +++
 include/hw/pci-host/i440fx.h     |   2 +
 include/hw/pci-host/pam.h        |  19 ++-
 include/hw/pci-host/q35.h        |   2 +
 softmmu/memory.c                 |  58 +++++++++-
 softmmu/physmem.c                |   5 +
 tests/data/acpi/q35/SSDT.dimmpxm | Bin 734 -> 734 bytes
 tests/qtest/i440fx-test.c        |  31 ++---
 14 files changed, 353 insertions(+), 95 deletions(-)

Comments

Lev Kujawski June 30, 2022, 12:50 a.m. UTC | #1
As detailed in the first patch of this series (8e64de1c), the
previously contiguous RAM aliased for the i440FX and Q35 machines was
broken into conventional [0-0xA0000] and extended regions
[0x100000-...], creating a need for a new E820 entry to account for
the ISA MMIO area gap.  This new entry slightly reduces the available
RAM, thus in the Q35's DSDT, the following change occurred:

<     Name (MEMA, 0x07FFF000)
>     Name (MEMA, 0x07FFE000)

accompanied by a corresponding change of checksum.  This patch updates
the above-referenced file to forestall the BIOS table test failure.

Signed-off-by: Lev Kujawski <lkujaw@member.fsf.org>
---
(v4) New patch.

 tests/data/acpi/q35/SSDT.dimmpxm | Bin 734 -> 734 bytes
 1 file changed, 0 insertions(+), 0 deletions(-)

diff --git a/tests/data/acpi/q35/SSDT.dimmpxm b/tests/data/acpi/q35/SSDT.dimmpxm
index 98e6f0e3f3bb02dd419e36bdd1db9b94c728c406..ac55387d57e48adb99eb738a102308688a262fb8 100644
GIT binary patch
delta 23
fcmcb|dXJSWIM^lR9uortW7tNni%iT9{<8xBTM-An

delta 23
fcmcb|dXJSWIM^lR9uortquWNVi%iTP{<8xBTCoSc
diff mbox

Patch

--- a/src/fw/shadow.c
+++ b/src/fw/shadow.c
@@ -28,7 +28,7 @@  union pamdata_u {

 // Enable shadowing and copy bios.
 static void
-__make_bios_writable_intel(u16 bdf, u32 pam0)
+make_bios_writable_intel(u16 bdf, u32 pam0)
 {
     // Read in current PAM settings from pci config space
     union pamdata_u pamdata;
@@ -39,11 +39,11 @@  __make_bios_writable_intel(u16 bdf, u32 pam0)
     // Make ram from 0xc0000-0xf0000 writable
     int i;
     for (i=0; i<6; i++)
-        pam[i + 1] = 0x33;
+        pam[i + 1] = 0x22;

     // Make ram from 0xf0000-0x100000 writable
     int ram_present = pam[0] & 0x10;
-    pam[0] = 0x30;
+    pam[0] = 0x20;

     // Write PAM settings back to pci config space
     pci_ioconfig_writel(bdf, ALIGN_DOWN(pam0, 4), pamdata.data32[0]);
@@ -54,24 +54,17 @@  __make_bios_writable_intel(u16 bdf, u32 pam0)
         memcpy(VSYMBOL(code32flat_start)
                , VSYMBOL(code32flat_start) + BIOS_SRC_OFFSET
                , SYMBOL(code32flat_end) - SYMBOL(code32flat_start));
-}

-static void
-make_bios_writable_intel(u16 bdf, u32 pam0)
-{
-    int reg = pci_ioconfig_readb(bdf, pam0);
-    if (!(reg & 0x10)) {
-        // QEMU doesn't fully implement the piix shadow capabilities -
-        // if ram isn't backing the bios segment when shadowing is
-        // disabled, the code itself won't be in memory.  So, run the
-        // code from the high-memory flash location.
-        u32 pos = (u32)__make_bios_writable_intel + BIOS_SRC_OFFSET;
-        void (*func)(u16 bdf, u32 pam0) = (void*)pos;
-        func(bdf, pam0);
-        return;
-    }
-    // Ram already present - just enable writes
-    __make_bios_writable_intel(bdf, pam0);
+    // Make ram from 0xc0000-0xf0000 writable
+    for (i=0; i<6; i++)
+        pam[i + 1] = 0x33;
+
+    // Make ram from 0xf0000-0x100000 writable
+    pam[0] = 0x30;
+
+    // Write PAM settings back to pci config space
+    pci_ioconfig_writel(bdf, ALIGN_DOWN(pam0, 4), pamdata.data32[0]);
+    pci_ioconfig_writel(bdf, ALIGN_DOWN(pam0, 4) + 4, pamdata.data32[1]);
 }

Lev Kujawski (3):