VOGONS


Finding bugs in 8086-80386 emulation core?

Topic actions

Reply 20 of 142, by peterferrie

User metadata
Rank Oldbie
Rank
Oldbie

You have a bug in popa. Compare:

00:03:56:75.07504: 0000:7D3C (60)PUSHA
00:03:56:75.07504: Registers:
00:03:56:75.07520: EAX: 00000000, EBX: 00000700, ECX: 00000001, EDX: 00000000

00:04:10:57.06960: 0000:7D71 (61)POPA
00:04:11:20.06368: EAX: 00007c7a, EBX: 00000000, ECX: 00000000, EDX: 00000001

Looks like a stack imbalance. From there:
00:04:30:64.06528: EAX: 00000201, EBX: 0000007c, ECX: 00000029, EDX: 0000c3c0

This request fails, and you get the crash.

Reply 21 of 142, by superfury

User metadata
Rank l33t++
Rank
l33t++

Something I do notice, is that the SP register is exactly 0x10 higher after the INT 13h call returns(with 4 bytes in memory being skipped in the log). So maybe some problem in either the INT13h handler is occurring, or the code that executes directly after it returns(those missing 4 bytes of instruction data in the log) does something to the SP register?

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 22 of 142, by superfury

User metadata
Rank l33t++
Rank
l33t++

Looking at the instruction directly after returning from the interrupt 13h handler: it's an LEA SP,[DS:SI+10], which is encoded as 8Dh, 64h, 10h at 0000:7D6E. Then it gets to the POPA instruction, which is popping the wrong data.

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 23 of 142, by superfury

User metadata
Rank l33t++
Rank
l33t++

This is a newly made log of the current commit of UniPCemu:

Filename
debugger_20170717_2128_complete.zip
File size
220.96 KiB
Downloads
55 downloads
File comment
Latest dump of Windows 95 volume boot sector executing.
File license
Fair use/fair dealing exception

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 24 of 142, by superfury

User metadata
Rank l33t++
Rank
l33t++

Thinking about it: SI should be 10h lower than the address of the place the PUSHA has pushed it's data? So the value of SI should be 0x7BAE, according to the instruction after the INT 13h(0x7BBE minus 0x10) and after the PUSHA?

Edit: Just looked for occurrences of "SI,"(without quotation marks). It only looks to be used and modified at a few places, but they should've been intentional?

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 25 of 142, by Jepael

User metadata
Rank Oldbie
Rank
Oldbie

So do you correctly handle size override prefixes (66)?

For example, it's 16-bit code, so all data and address sizes are 16-bit unless data/address size overrides are used.

6a XX : push imm8 as 16-bit word
66 6a XX : push imm8 as 32-bit doubleword

Reply 26 of 142, by vladstamate

User metadata
Rank Oldbie
Rank
Oldbie

Does 66 6A XX modify ESP or SP ?

What about 67 6A XX ?

YouTube channel: https://www.youtube.com/channel/UC7HbC_nq8t1S9l7qGYL0mTA
Collection: http://www.digiloguemuseum.com/index.html
Emulator: https://sites.google.com/site/capex86/
Raytracer: https://sites.google.com/site/opaqueraytracer/

Reply 27 of 142, by superfury

User metadata
Rank l33t++
Rank
l33t++

The operand size override will make it push/pop 32-bit registers and data on the stack and move stack data up or down 4 instead of 2 bytes(+/-=4 vs +/-=2) in real mode.
The address size override(0x67) has no effect on stack, only modr/m and mov [imm16/32],al/ax/eax instructions. So it's ineffective with PUSHA/POPA.

The code segment descriptor D-bit determines the default operand size. This is flipped by the operand size override.
The stack segment descriptor B-bit will make the stack use ESP instead of SP.

Those overrides are unused with the mentioned code that's running.

Edit: The immediate stays 8-bit, just pushing 32-bits of data on the stack(zero-extended), decreasing SP with 4, when used with the operand-size prefix. Address size prefix has no effect.

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 28 of 142, by vladstamate

User metadata
Rank Oldbie
Rank
Oldbie

No it is not. 0x6A is PUSH imm8. I know your code had PUSHA as the opcode in question but I guess me and Japael meant PUSH imm.

Providing a 16bit segment. If I have the 66 or 67 prefix, will ESP or SP be modified? I assume 66 pushes a 32bit value on the stack and 67 modified ESP.

YouTube channel: https://www.youtube.com/channel/UC7HbC_nq8t1S9l7qGYL0mTA
Collection: http://www.digiloguemuseum.com/index.html
Emulator: https://sites.google.com/site/capex86/
Raytracer: https://sites.google.com/site/opaqueraytracer/

Reply 29 of 142, by superfury

User metadata
Rank l33t++
Rank
l33t++

Currently, 66h works as you say. But 67h only has effect on modr/m and mov to/from al/ax/eax with immediate offset(opcodes A0-A3).

Wouldn't it cause problems if the stack size(SP vs ESP) can be overridden by 67h? Like with 67h PUSH [DS:ESI]? So both the parameters to store data(DS:ESI) and the stack itself((E)SP) would switch? That shouldn't be the case?

Edit: https://c9x.me/x86/html/file_module_x86_id_269.html confirms this, basically.

Edit: http://www.felixcloutier.com/x86/PUSH.html also confirms only the SS Segment Descriptor B-bit is used to differentiate between SP and ESP during stack accesses.

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 31 of 142, by superfury

User metadata
Rank l33t++
Rank
l33t++

I've just fixed a little bug in the FDC seek/recalibrate(Missing seek bit in MSR and IRQ) and Specify(Missing IRQ) commands. Now the Compaq Deskpro 386 BIOS hangs with POST Diagnostics code being A8? So problem detecting drive type? AT still fails the FDC after seeking?

Edit: Looking at the executed code, it keeps executing the same code in a loop after setting drive 3 motor to ON:

Looptop:
IN AL,40h
MOV AH,AL
IN AL,40h
SUB AL,AH
JA Looptop

Looking onwards, I see the BIOS setting 40:90 to 00h, with no new FDC commands executed after that? The hang seems to be out there?

Log made of the BIOS running:
https://www.dropbox.com/s/im4907h8vm98uja/deb … 24_2113.7z?dl=0

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 32 of 142, by superfury

User metadata
Rank l33t++
Rank
l33t++

Having looked at osdev.org's FDC information, my Floppy Specify command(a.k.a. Fix drive data) was generating an IRQ, which it shouldn't(apparently). Fixing this, the Compaq Deskpro 386 BIOS boots without problems again.

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 33 of 142, by superfury

User metadata
Rank l33t++
Rank
l33t++

I'm trying to get the FDC working properly again on the XT(with a 80386 without any waitstates for faster testing), but for some reason, my floppy disk boots fine, until it's past the HIMEM.SYS driver, after which the floppy disk controller goes awry for some reason? It says:

Bad or missing VIDE-CDD.SYS
Error in CONFIG.SYS line 4
HMA not available : Loading DOS low

Not ready reading drive A
Abort, Retry, Ignore, Fail?

The FDC data shows that the last (correctly) executed command was a Specify command. The MSR is 0xB0, the floppy being ready to receive a new command. Specify doesn't raise any IRQ(which is according to various sources, like osdev and 82077AA datasheet). The MSR isn't read(and updated as such) after the specify command received it's parameters and executed.

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 34 of 142, by superfury

User metadata
Rank l33t++
Rank
l33t++

This is a log of the entire FDC booting MS-DOS 5.0 with HIMEM.SYS, then failing on the remaining parts:

406.jpg
Filename
406.jpg
File size
40.65 KiB
Views
576 views
File comment
Screen capture directly after the log.
File license
Fair use/fair dealing exception
Filename
debugger.log
File size
369.52 KiB
Downloads
40 downloads
File comment
Floppy disk log of everything the FDC does and gotten reads/writes.
File license
Fair use/fair dealing exception

Can anyone see what's going wrong?

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 35 of 142, by superfury

User metadata
Rank l33t++
Rank
l33t++

I've just tried copying the Windows 3.0 setup files(valid files) from CD-ROM ISO image using the Compaq Deskpro 386 emulation, then installing Windows 3.0 on the NEC V30 XT configuration. The AT drivers(himem.sys, vide-cdd.sys) abort loading because of the 'non-x86' CPU(although it might need a 32-bit x86 CPU, so it means IA32 instead of x86-16? Then it continues loading the remaining drivers(ctmouse.exe and mscdex.exe), where mscdex fails because no drivers for the CD-ROM(vide-cdd.sys) are found. Then, when I start setup.exe(the files check out being copied correctly by extracting them using Winimage and using Winmerge to compare the directories) everything works correctly, until it starts the kernel/win.com(black screen after copying the first two disks). At that point, the application hangs because of an unknown CPU bug.

So that means the 8086/80186 emulation cores have a bug(NEC V30 is actually a 80186, with 8086 cycle-accurate timing and 4 cycles/instruction for all 80186 instructions EU timings)? Is there a good way to find the offending instruction?

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 36 of 142, by superfury

User metadata
Rank l33t++
Rank
l33t++

Trying to find a simple testsuite for the 80386 leads me to this: http://marc.info/?l=bochs-dev&m=124236420804902

But, unfortunately, it seems to contain stuff for an FPU and/or newer unsupported CPUs as well. Currently only up to 80486SX is implemented(Pentium would be tough, seeing as it has parallel processing etc., so I doubt I'll start on that anytime soon(also the caches are going to be hard to implement, let alone with speed).

Are there any testsuites for 80386(all instructions/opcodes) available?

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 37 of 142, by superfury

User metadata
Rank l33t++
Rank
l33t++

Just tried installing Windows 3.0 with the CGA emulation and NEC V30 XT(80186) configuration. Windows 3.0 setup continues past given point, until it gets to disk 4, after which the keyboard becomes unresponsive for some unknown reason. Restarting win.com from the command line makes it continue at disk 4, while also not receiving any keyboard input. Since the CGA drivers don't use any 80186 instructions(afaik), that means there's a serious problem with the 8086 emulation core?

8086 emulation core: https://bitbucket.org/superfury/unipcemu/src/ … 086.c?at=master

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 38 of 142, by danoon

User metadata
Rank Member
Rank
Member

I also was unable to find any test suites for x86 emulation when I was working on jDosbox. The closest I came to finding one was for the FPU. I ended up writing my own unit tests, but it's not complete, it mainly deals with math instruction and making sure I handled flags correctly. Even though it took a while to write, I believe it more than paid off, especially when I tried to come up with a new core. I would recommend the same for you. And I feel you pain on debugging those issues. I was spent 2 weeks tracking down a single cpu bug that prevented Windows XP from booting.

https://sourceforge.net/p/jdosbox/code/HEAD/t … u/instructions/

http://www.boxedwine.org/

Reply 39 of 142, by superfury

User metadata
Rank l33t++
Rank
l33t++

Currently converting much of the Ev vs Gv logic to use the lookup tables instead(only up to 80186 so far), but for some still unknown reason, the Turbo XT BIOS crashes on the VGA, according to it's beep codes(not crashing 2 commits back). I'm also considering converting the protection/interrupt module to become fully cycle-accurate(e.g. Using the BIU to fetch all data, needing to interrupt execution in between), but I'm not sure what's the best way to implement that change. How does a real CPU handle this? Does it contain some microcode to handle that(everything protection/exception/interrupt/task switch-related)? Are those supposed to be one execution path? Is the path aborted during exceptions/task switches executing a path? How does a real CPU handle this, theoretically? What kind of 'scripts' does it run to handle all those(probaby implemented in microcode)? I need to make it in some semi-script form in order for it to be made compatible with the cycle-accurate BIU(which can halt the then-used script while it's fetching data from RAM or storing data to RAM). Of course, exceptions terminate the script and starts a new one(for the exception handler, resetting all registers to the current task state or instruction state(in real mode).

Current commit(which breaks emulation, causing the VGA BIOS to fail): https://bitbucket.org/superfury/unipcemu/comm … f8647?at=master

Two commits earlier( https://bitbucket.org/superfury/unipcemu/comm … f7abf?at=master ) still ran without known problems(on the 8086/80186 core).

Can anyone see the error(s)? Why is the VGA BIOS failing? Anyone has any ideas on implementing the protected mode features using such a (semi-)script(still plain C though)?

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io