VOGONS


First post, by Rav

User metadata
Rank Member
Rank
Member

Hi,

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?

Reply 1 of 5, by Rav

User metadata
Rank Member
Rank
Member

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?

Super IO specs/progs info attached.

FDC37C665GT.PDF

Reply 3 of 5, by Rav

User metadata
Rank Member
Rank
Member
Rwolf wrote on 2024-05-21, 22:04:

There is this bios: https://archive.org/details/ecs-al486

I'm not sure if it matches your board though?

Seam to be the same rom as https://theretroweb.com/motherboards/s/ecs-al486
It's the version without the super io so I doubt it will work, I will still try.

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)

Reply 4 of 5, by Rav

User metadata
Rank Member
Rank
Member

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.

full board.jpeg

Reply 5 of 5, by Rav

User metadata
Rank Member
Rank
Member

Op success!

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 :

use16        ; ISA module operates in the 16-bit segment.


ROM_SIZE_IN_BLOCK = 16 ; 16 means ROM size is 16 block (8192 bytes)
ROM_SIZE_IN_BYTE = ROM_SIZE_IN_BLOCK * 512

DB 0x55, 0xAA ; Boot signature
DB 0x10 ; Block size in sectors (200h each)

start:

pusha ; Save all registers into stack
cli ; Disabling interrupt
mov ax,cs ; Update ds and es using the actual code pointer that start at the 4th byte
mov ds,ax ; As byte 1 & 2 is the magic and byte 3 is the lenght of the rom
mov es,ax

mov si, hello_string ; Put string location into SI
call print_string ; Call our string-printing routine

call unlock_chipset ; We unlock the chipset

; Now we set register to patch in CL and value in CH and mask in BL

; 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
mov bl,0xF8
mov al,0x20
mov ah,0x01
call setRegister

; READ MEMORY TIMING MASK = 0xFC; REGISGER = 0x16, 0x03 = Fastest, 0x02 = Fast, 0x01 = Slow, 0x00 = Slowest
mov bl,0xFC
mov al,0x16
mov ah,0x03
call setRegister

; WRITE MEMORY TIMING MASK = 0xFC; REGISGER = 0x16, 0x0C = Fastest, 0x08 = Fast, 0x04 = Slow, 0x00 = Slowest
mov bl,0xF3
mov al,0x16
mov ah,0x08
call setRegister

; L2 cache read WS MASK = 0xBF; REGISGER = 0x19, 0x00 = 0WS, 0x40 = 1WS
mov bl,0xBF
mov al,0x19
mov ah,0x40
call setRegister

; L2 cache write WS MASK = 0xDF; REGISGER = 0x19, 0x00 = 0WS, 0x20 = 1WS
mov bl,0xDF
mov al,0x19
mov ah,0x00
call setRegister

; Hidden Refresh MASK = 0xEF; REGISGER = 0x12, 0x00 = Disabled, 0x10 = enabled
mov bl,0xEF
mov al,0x12
mov ah,0x10
call setRegister

Show last 154 lines
; HITMJ MASK = 0xCF; REGISGER = 0x17, 0x00 = 2t, 0x10 = 3t, 0x20 = 4t, 0x30 = 5t
mov bl,0xCF
mov al,0x17
mov ah,0x10
call setRegister

; Cycle Check Point MASK = 0xFC; REGISGER = 0x17, 0x01 = fast, 0x02 = normal, 0x03 = slow
mov bl,0xFC
mov al,0x17
mov ah,0x01
call setRegister

; ISA Write Cycle MASK = 0xFB; REGISGER = 0x22, 0x00 = 0WS, 0x04 = 1WS
mov bl,0xFB
mov al,0x22
mov ah,0x00
call setRegister

;;;;;;;;;;;;;;;;;;;;;;;;;;;;; VESA Master Cycle ADSJ
;;; to
;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ISA Command Wait time

; RAS to CAS delay MASK = 0x3F; REGISGER = 0x1A, 0x00 = 2t, 0x40 = 4t, 0x80 = 6t
mov bl,0x3F
mov al,0x1A
mov ah,0x00
call setRegister

; Slow Refresh MASK = 0xCF; REGISGER = 0x25, 0x00 = Disabled, 0x10 = 30us, 0x20 = 60us, 0x30 = 120us
mov bl,0xCF
mov al,0x25
mov ah,0x30
call setRegister

; SWITCH TO WT
wbinvd
call flushCache
mov bl,0xF7
mov al,0x19
mov ah,0x00
call setRegister
call flushCache

popa ; We restore the registers from stack before returning to the BIOS
retf ; We return to BIOS


flushCache:
pusha ; System have 256KB worth of cache (the max it can accept)
mov ax,0x0000; ; So I'm just reading the first 640KB of ram
mov es,ax; ; To flush the L2.
mov bx,0x0000;

.loopMem1:
mov ax,[es:bx];
add bx,0x0010; ; Cache line is 16 bytes... riiiight??? So I can increment by 16... hopefully. Seam to work and a lot faster
cmp bx,0x0000;
jne .loopMem1

mov ax,es;
add ax,0x1000;
mov es,ax;
cmp ax,0xA000;
jne .loopMem1

popa
ret

setRegister:
cli
out 0x22,al ; We set the register to patch
jmp $+2 ; Wait time
jmp $+2 ; Wait time
in al,0x23 ; we load the old value

and al,bl ; We apply the mask to old register value
or al,ah ; We patch the value 1

out 0x23,al ; We write new register
sti
ret


unlock_chipset:
cli
mov al,0x03
out 0x22,al
mov al,0xc5
out 0x23,al
xor al,al

in al,0x23
sti
cmp al,0xc5
jne nounlock
ret

nounlock:
mov si, hello_string ; Put string location into SI
call print_string ; Call our string-printing routine
.nounlock2:
jmp .nounlock2

print_string: ; Routine: output string in SI to screen

.repeat:
mov ah, 09h ; int 10h 'print char' function
mov bh, 0x00
mov bl, 0x03
mov cx, 01h
cld ; Clears the DF flag in the EFLAGS register. When the DF flag is set to 0, string operations increment the index registers (SI).
lodsb ; Load byte at address DS:SI into AL then increment SI by one (Becose of previous line)
cmp al, 0 ; If al is 00, then we are at the end of the string
je .done ; In that case, where done!


; If char is zero, end of string
int 10h ; Otherwise, print it
mov bh, 00h ; Then all the rest till the jmp, we are just moving cursor forward
mov ah, 03h
int 10h
mov ah, 02h
mov bh, 00h
inc dl
int 10h
jmp .repeat

.done:
mov bh, 00h ; Here we just move cursor to beginning and go down one line
mov ah, 03h
int 10h
mov ah, 02h
mov bh, 00h
inc dh
xor dl,dl
int 10h

ret

hello_string db "ALI1429 Boot patcher v0.1 (C)2024 Rav @ Vogons.org", 0x00
unable_unlock_string db "Unable to unlock the chipset :(", 0x00

times (ROM_SIZE_IN_BYTE-$) db 0 ; use 00h as the padding bytes until we reach the ROM size

; Thanks Stack Overflow for the following code
; https://stackoverflow.com/questions/49001298/option-rom-code-failing-to-print-intended-string-using-qemu-emulation
;patch_byte is calculated and automagically inserted below
PREV_CHKSUM = 0
repeat $
load CHKSUM byte from %-1
CHKSUM = (PREV_CHKSUM + CHKSUM) mod 0x100
PREV_CHKSUM = CHKSUM
end repeat
store byte (0x100 - CHKSUM) at ($-1) ; store the patch_byte