I want to replace the BIOS of my Acer A1GX-2 motherboard for another one that have proper settings options (for sram/dram timings and pretty much all the stuff I have implemented into my "Universal Chipset Patcher" program). Main reason is that when I boot the system, some of the things are really borked by default, for example, the ATBUS is too slow when booting the Cyrix 5x86 with a 40Mhz BUS (keyboard do bip bip bip at half of the keypress) and so, if I want to boot other OS than DOS or Windows 95, I have to first boot on DOS so my chipset patcher run and patch everything correctly then I have to "fast reboot, using QEMM" to reboot on another operating system, like NT4, without resetting the current chipset configurations.
The following board have bios that have all the option (according to its manual) and also seam to have the same Super IO chip : ECS AL486 VIO-U3/VIO-I
But the BIOS is not on retroweb and I could not find it.
Other maybe solution would be to use MiTAC MSC-242 or 246 BIOS (Could also not find them). I am not totally sure they have the same super-io, I could only visually decode the word "SMC" but not the small numbers, from pictures, but who know, could work... maybe.
Does someone saw these somewhere or had more luck than me?
Well, I'm thinking about just flashing the motherboard eprom with a ROM from a board without superio
And just making an option rom I can pluck on my network card to configure the super io.
According to the datasheet, the whole collection of thing on that super io should turn on at there default address at boot (IDE, Floppy, serials and parallel). So technically I would just need to disable the serials and parallel because i'm not using them and leave the rest as is right?
I'm going to dump all the superio registers while making the rom to be sure there is nothing else that need to be configured.
You think it should work? Like the IDE/Floppy configurator from another BIOS should allow me to configure it like if it was a random super io ISA card?
I will try it but at least I just managed to make an ISA option rom that boot so I can try to configure with the super io that way now if I can't find a proper bios.
Or the opposite, keeping the crap Acer BIOS and just patch the chipset register that way instead of having my program to configure them from the autoexec.bat, that would also give me the same purpose (booting any OS and have the keyboard to work properly)
Finally I did test with different bios. (Most without SuperIO, one with a very similar one)
They all produced beep code related to memory error (removing the memory did produce a different kind of beep, at least on the AMI one).
Something I did not take into account is that my board have one extra chip that none of the other board with that chipset seam to have, ALI M5213N. It is strategically placed between the CPU and the cache memory and for sure, there are trace that go to the cache. So I assume mine have extra "spacial undocumented things". I could not find the specs of that chip.
So I'm going to go with plan B, Simply flash the Chipset patchs into a 8KB EPROM that I will place on my network card instead of trying to get another BIOS that have actual option to set the stuff.
I am going to send the original A1GX-2 BIOS dump to the retro web next time I turn on my laptop as they don't have it.
I did attach a "OLD" picture of the board on where we can see the chip.
While I could not change the BIOS, I managed to make an option ROM (am27c64) for my 3COM 3C509-B and it just work. Option rom load, patch the registers and change the cache to write-thru.
While i'm at it, I might add the Cyrix 5x86 shenanigans in there too...
Here is the code :
1use16 ; ISA module operates in the 16-bit segment. 2 3 4ROM_SIZE_IN_BLOCK = 16 ; 16 means ROM size is 16 block (8192 bytes) 5ROM_SIZE_IN_BYTE = ROM_SIZE_IN_BLOCK * 512 6 7DB 0x55, 0xAA ; Boot signature 8DB 0x10 ; Block size in sectors (200h each) 9 10start: 11 12 pusha ; Save all registers into stack 13 cli ; Disabling interrupt 14 mov ax,cs ; Update ds and es using the actual code pointer that start at the 4th byte 15 mov ds,ax ; As byte 1 & 2 is the magic and byte 3 is the lenght of the rom 16 mov es,ax 17 18 mov si, hello_string ; Put string location into SI 19 call print_string ; Call our string-printing routine 20 21 call unlock_chipset ; We unlock the chipset 22 23; Now we set register to patch in CL and value in CH and mask in BL 24 25; ATBUS MASK = 0xF8; REGISGER = 0x20, 0x00 = 7.19Mhz, 0x01 = CLK/4, 0x02 = CLK/5, 0x03 = CLK/6, 0x04 = CLK/8, 0x05 = CLK/10, 0x06 = CLK/12 26 mov bl,0xF8 27 mov al,0x20 28 mov ah,0x01 29 call setRegister 30 31; READ MEMORY TIMING MASK = 0xFC; REGISGER = 0x16, 0x03 = Fastest, 0x02 = Fast, 0x01 = Slow, 0x00 = Slowest 32 mov bl,0xFC 33 mov al,0x16 34 mov ah,0x03 35 call setRegister 36 37; WRITE MEMORY TIMING MASK = 0xFC; REGISGER = 0x16, 0x0C = Fastest, 0x08 = Fast, 0x04 = Slow, 0x00 = Slowest 38 mov bl,0xF3 39 mov al,0x16 40 mov ah,0x08 41 call setRegister 42 43; L2 cache read WS MASK = 0xBF; REGISGER = 0x19, 0x00 = 0WS, 0x40 = 1WS 44 mov bl,0xBF 45 mov al,0x19 46 mov ah,0x40 47 call setRegister 48 49; L2 cache write WS MASK = 0xDF; REGISGER = 0x19, 0x00 = 0WS, 0x20 = 1WS 50 mov bl,0xDF 51 mov al,0x19 52 mov ah,0x00 53 call setRegister 54 55; Hidden Refresh MASK = 0xEF; REGISGER = 0x12, 0x00 = Disabled, 0x10 = enabled 56 mov bl,0xEF 57 mov al,0x12 58 mov ah,0x10 59 call setRegister 60
…Show last 154 lines
61; HITMJ MASK = 0xCF; REGISGER = 0x17, 0x00 = 2t, 0x10 = 3t, 0x20 = 4t, 0x30 = 5t 62 mov bl,0xCF 63 mov al,0x17 64 mov ah,0x10 65 call setRegister 66 67; Cycle Check Point MASK = 0xFC; REGISGER = 0x17, 0x01 = fast, 0x02 = normal, 0x03 = slow 68 mov bl,0xFC 69 mov al,0x17 70 mov ah,0x01 71 call setRegister 72 73; ISA Write Cycle MASK = 0xFB; REGISGER = 0x22, 0x00 = 0WS, 0x04 = 1WS 74 mov bl,0xFB 75 mov al,0x22 76 mov ah,0x00 77 call setRegister 78 79;;;;;;;;;;;;;;;;;;;;;;;;;;;;; VESA Master Cycle ADSJ 80;;; to 81;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ISA Command Wait time 82 83; RAS to CAS delay MASK = 0x3F; REGISGER = 0x1A, 0x00 = 2t, 0x40 = 4t, 0x80 = 6t 84 mov bl,0x3F 85 mov al,0x1A 86 mov ah,0x00 87 call setRegister 88 89; Slow Refresh MASK = 0xCF; REGISGER = 0x25, 0x00 = Disabled, 0x10 = 30us, 0x20 = 60us, 0x30 = 120us 90 mov bl,0xCF 91 mov al,0x25 92 mov ah,0x30 93 call setRegister 94 95; SWITCH TO WT 96 wbinvd 97 call flushCache 98 mov bl,0xF7 99 mov al,0x19 100 mov ah,0x00 101 call setRegister 102 call flushCache 103 104 popa ; We restore the registers from stack before returning to the BIOS 105 retf ; We return to BIOS 106 107 108flushCache: 109 pusha ; System have 256KB worth of cache (the max it can accept) 110 mov ax,0x0000; ; So I'm just reading the first 640KB of ram 111 mov es,ax; ; To flush the L2. 112 mov bx,0x0000; 113 114 .loopMem1: 115 mov ax,[es:bx]; 116 add bx,0x0010; ; Cache line is 16 bytes... riiiight??? So I can increment by 16... hopefully. Seam to work and a lot faster 117 cmp bx,0x0000; 118 jne .loopMem1 119 120 mov ax,es; 121 add ax,0x1000; 122 mov es,ax; 123 cmp ax,0xA000; 124 jne .loopMem1 125 126 popa 127ret 128 129setRegister: 130 cli 131 out 0x22,al ; We set the register to patch 132 jmp $+2 ; Wait time 133 jmp $+2 ; Wait time 134 in al,0x23 ; we load the old value 135 136 and al,bl ; We apply the mask to old register value 137 or al,ah ; We patch the value 1 138 139 out 0x23,al ; We write new register 140 sti 141ret 142 143 144unlock_chipset: 145 cli 146 mov al,0x03 147 out 0x22,al 148 mov al,0xc5 149 out 0x23,al 150 xor al,al 151 152 in al,0x23 153 sti 154 cmp al,0xc5 155 jne nounlock 156ret 157 158nounlock: 159 mov si, hello_string ; Put string location into SI 160 call print_string ; Call our string-printing routine 161 .nounlock2: 162 jmp .nounlock2 163 164print_string: ; Routine: output string in SI to screen 165 166 .repeat: 167 mov ah, 09h ; int 10h 'print char' function 168 mov bh, 0x00 169 mov bl, 0x03 170 mov cx, 01h 171 cld ; Clears the DF flag in the EFLAGS register. When the DF flag is set to 0, string operations increment the index registers (SI). 172 lodsb ; Load byte at address DS:SI into AL then increment SI by one (Becose of previous line) 173 cmp al, 0 ; If al is 00, then we are at the end of the string 174 je .done ; In that case, where done! 175 176 177 ; If char is zero, end of string 178 int 10h ; Otherwise, print it 179 mov bh, 00h ; Then all the rest till the jmp, we are just moving cursor forward 180 mov ah, 03h 181 int 10h 182 mov ah, 02h 183 mov bh, 00h 184 inc dl 185 int 10h 186 jmp .repeat 187 188 .done: 189 mov bh, 00h ; Here we just move cursor to beginning and go down one line 190 mov ah, 03h 191 int 10h 192 mov ah, 02h 193 mov bh, 00h 194 inc dh 195 xor dl,dl 196 int 10h 197 198ret 199 200hello_string db "ALI1429 Boot patcher v0.1 (C)2024 Rav @ Vogons.org", 0x00 201unable_unlock_string db "Unable to unlock the chipset :(", 0x00 202 203times (ROM_SIZE_IN_BYTE-$) db 0 ; use 00h as the padding bytes until we reach the ROM size 204 205; Thanks Stack Overflow for the following code 206; https://stackoverflow.com/questions/49001298/option-rom-code-failing-to-print-intended-string-using-qemu-emulation 207 ;patch_byte is calculated and automagically inserted below 208PREV_CHKSUM = 0 209repeat $ 210 load CHKSUM byte from %-1 211 CHKSUM = (PREV_CHKSUM + CHKSUM) mod 0x100 212 PREV_CHKSUM = CHKSUM 213end repeat 214store byte (0x100 - CHKSUM) at ($-1) ; store the patch_byte