idea: add option to switch off A20 gate automatically on EXEC if DOS program is being loaded below the 64KB mark that would require LOADFIX -a. Real DOS doesn't do this, so the option is off by default.

This commit is contained in:
Jonathan Campbell 2025-01-29 16:47:22 -08:00
parent bbd3f69760
commit 5d01c5f13e
3 changed files with 19 additions and 0 deletions

View File

@ -94,6 +94,7 @@ bool SwitchLanguage(int oldcp, int newcp, bool confirm);
void makestdcp950table(), makeseacp951table();
std::string GetDOSBoxXPath(bool withexe=false);
extern std::string prefix_local, prefix_overlay;
bool a20_off_if_loading_low=true;
int ascii_toupper(int c) {
if (c >= 'a' && c <= 'z')
@ -4143,6 +4144,7 @@ public:
minimum_mcb_segment = section->Get_hex("minimum mcb segment");
private_segment_in_umb = section->Get_bool("private area in umb");
private_segment_write_protect = section->Get_bool("private area write protect");
a20_off_if_loading_low = section->Get_bool("turn off a20 gate on load if loadfix needed");
enable_collating_uppercase = section->Get_bool("collating and uppercase");
private_always_from_umb = section->Get_bool("kernel allocation in umb");
minimum_dos_initial_private_segment = section->Get_hex("minimum dos initial private segment");

View File

@ -31,6 +31,12 @@
#include "menu.h"
#include "crc32.h"
extern bool xms_init;
extern bool a20_off_if_loading_low;
Bitu XMS_EnableA20(bool enable);
Bitu XMS_GetEnabledA20(void);
uint32_t RunningProgramHash[4] = {0,0,0,0};
uint32_t RunningProgramLoadAddress = 0;
@ -554,6 +560,11 @@ bool DOS_Execute(const char* name, PhysPt block_pt, uint8_t flags) {
RunningProgramHash[3] = 0;
}
if (a20_off_if_loading_low && pspseg < 0x1000 && xms_init && XMS_GetEnabledA20() && !(cpu.cr0 & CR0_PROTECTION)/*not protected/vm86 mode*/) {
LOG(LOG_EXEC,LOG_DEBUG)("Program is being loaded below 64KB, disabling A20 gate to try to avoid some common crashes");
XMS_EnableA20(false);
}
if (flags==LOAD) {
/* First word on the stack is the value ax should contain on startup */
real_writew(RealSeg(sssp-2),RealOff(sssp-2),reg_bx);

View File

@ -4454,6 +4454,12 @@ void DOSBOX_SetupConfigSections(void) {
Pbool->Set_help("Enable XMS support.");
Pbool->SetBasic(true);
/* maybe this will stop the endless "it's broken and it only works once you point out LOADFIX -a" bug reports */
Pbool = secprop->Add_bool("turn off a20 gate on load if loadfix needed",Property::Changeable::WhenIdle,false);
Pbool->Set_help("If enabled, and loading a program below the 64kb boundary, turn off the A20 gate.\n"
"This can help with any program with startup code that assumes the segment wraparound of the 8086.\n"
"Depending on DOS configuration the A20 gate may be re-enabled later such as calling INT 21h.");
Pbool = secprop->Add_bool("xms memmove causes flat real mode",Property::Changeable::WhenIdle,true);
Pbool->Set_help("If set, any call to XMS to move/copy memory sets up flat real mode for segment registers DS and ES.");