From: Izik Eidus <izike@qumranet.com>

add support to memory above the pci hole
    
the new memory region is mapped after address 0x100000000,
the bios take the size of the memory after the 0x100000000 from
three new cmos bytes.

diff --git a/bios/rombios.c b/bios/rombios.c
index 1be0816..b70f249 100644
--- a/bios/rombios.c
+++ b/bios/rombios.c
@@ -4442,22 +4442,25 @@ BX_DEBUG_INT15("case default:\n");
 #endif // BX_USE_PS2_MOUSE
 
 
-void set_e820_range(ES, DI, start, end, type)
+void set_e820_range(ES, DI, start, end, extra_start, extra_end, type)
      Bit16u ES;
      Bit16u DI;
      Bit32u start;
      Bit32u end;
+     Bit8u extra_start;
+     Bit8u extra_end;
      Bit16u type;
 {
     write_word(ES, DI, start);
     write_word(ES, DI+2, start >> 16);
-    write_word(ES, DI+4, 0x00);
+    write_word(ES, DI+4, extra_start);
     write_word(ES, DI+6, 0x00);
 
     end -= start;
+    extra_end -= extra_start;
     write_word(ES, DI+8, end);
     write_word(ES, DI+10, end >> 16);
-    write_word(ES, DI+12, 0x0000);
+    write_word(ES, DI+12, extra_end);
     write_word(ES, DI+14, 0x0000);
 
     write_word(ES, DI+16, type);
@@ -4470,7 +4473,9 @@ int15_function32(regs, ES, DS, FLAGS)
   Bit16u ES, DS, FLAGS;
 {
   Bit32u  extended_memory_size=0; // 64bits long
+  Bit32u  extra_lowbits_memory_size=0;
   Bit16u  CX,DX;
+  Bit8u   extra_highbits_memory_size=0;
 
 BX_DEBUG_INT15("int15 AX=%04x\n",regs.u.r16.ax);
 
@@ -4544,11 +4549,18 @@ ASM_END
                     extended_memory_size += (1L * 1024 * 1024);
                 }
 
+                extra_lowbits_memory_size = inb_cmos(0x5c);
+                extra_lowbits_memory_size <<= 8;
+                extra_lowbits_memory_size |= inb_cmos(0x5b);
+                extra_lowbits_memory_size *= 64;
+                extra_lowbits_memory_size *= 1024;
+                extra_highbits_memory_size = inb_cmos(0x5d);
+
                 switch(regs.u.r16.bx)
                 {
                     case 0:
                         set_e820_range(ES, regs.u.r16.di,
-                                       0x0000000L, 0x0009f000L, 1);
+                                       0x0000000L, 0x0009f000L, 0, 0, 1);
                         regs.u.r32.ebx = 1;
                         regs.u.r32.eax = 0x534D4150;
                         regs.u.r32.ecx = 0x14;
@@ -4557,7 +4569,7 @@ ASM_END
                         break;
                     case 1:
                         set_e820_range(ES, regs.u.r16.di,
-                                       0x0009f000L, 0x000a0000L, 2);
+                                       0x0009f000L, 0x000a0000L, 0, 0, 2);
                         regs.u.r32.ebx = 2;
                         regs.u.r32.eax = 0x534D4150;
                         regs.u.r32.ecx = 0x14;
@@ -4566,7 +4578,7 @@ ASM_END
                         break;
                     case 2:
                         set_e820_range(ES, regs.u.r16.di,
-                                       0x000e8000L, 0x00100000L, 2);
+                                       0x000e8000L, 0x00100000L, 0, 0, 2);
                         regs.u.r32.ebx = 3;
                         regs.u.r32.eax = 0x534D4150;
                         regs.u.r32.ecx = 0x14;
@@ -4577,7 +4589,7 @@ ASM_END
 #if BX_ROMBIOS32
                         set_e820_range(ES, regs.u.r16.di,
                                        0x00100000L,
-                                       extended_memory_size - ACPI_DATA_SIZE, 1);
+                                       extended_memory_size - ACPI_DATA_SIZE ,0, 0, 1);
                         regs.u.r32.ebx = 4;
 #else
                         set_e820_range(ES, regs.u.r16.di,
@@ -4593,7 +4605,7 @@ ASM_END
                     case 4:
                         set_e820_range(ES, regs.u.r16.di,
                                        extended_memory_size - ACPI_DATA_SIZE,
-                                       extended_memory_size, 3); // ACPI RAM
+                                       extended_memory_size ,0, 0, 3); // ACPI RAM
                         regs.u.r32.ebx = 5;
                         regs.u.r32.eax = 0x534D4150;
                         regs.u.r32.ecx = 0x14;
@@ -4603,7 +4615,20 @@ ASM_END
                     case 5:
                         /* 256KB BIOS area at the end of 4 GB */
                         set_e820_range(ES, regs.u.r16.di,
-                                       0xfffc0000L, 0x00000000L, 2);
+                                       0xfffc0000L, 0x00000000L ,0, 0, 2);
+                        if (extra_highbits_memory_size || extra_lowbits_memory_size)
+                            regs.u.r32.ebx = 6;
+                        else
+                            regs.u.r32.ebx = 0;
+                        regs.u.r32.eax = 0x534D4150;
+                        regs.u.r32.ecx = 0x14;
+                        CLEAR_CF();
+                        return;
+                    case 6:
+                        /* Maping of memory above 4 GB */
+                        set_e820_range(ES, regs.u.r16.di, 0x00000000L,
+                        extra_lowbits_memory_size, 1, extra_highbits_memory_size
+                                       + 1, 1);
                         regs.u.r32.ebx = 0;
                         regs.u.r32.eax = 0x534D4150;
                         regs.u.r32.ecx = 0x14;
