So I'm coding some stuff in assembly (TASM) for DOS with DOSBox (long story short: for our assembly course assignments the professor says we need to use an environment from the 90s for some reason, but anyway; regarding using a DOS VM instead… let's just say, it hasn't ended up working well, but this is kind of a tangent at this point, at least DOSBox runs fine for most purposes). In this program, I needed to use the FPU (with the .387
directive) to get some coordinates for drawing, everything else was completely fine, but this thing doesn't seem to be working.
Like, I have initialized the FPU using finit
in the beginning of the program, I'm trying to put different numbers in the stack using different commands like fild
with 16-bit or 32-bit values or fld
or fld1
or fldz
but none of those seem to be working: in Turbo Debugger, I open the numeric processor viewer and the whole FPU stack is just empty, absolutely nothing ever changes at all, no values get added or anything.
I don't think there's much code to show in here, since all of that is literally just one or two word-long assembly instructions that I already described above, and I feel like the problem is with my DOSBox configuration anyway. But right now I'm just stuck and I have absolutely no idea on what to do next
I feel like this information might be important too: I'm still trying to work in real mode (because I have absolutely no idea how to use protected mode, plus it's not really the point of the current assignment and I don't wanna add any more pain on top of all that I already have anyway): but since I can't use older 16-bit CPUs for some FPU functions like fsin
, I have to put these directives in the ASM file to make this unholy chimera (I call this “16.5 bit”™) since apparently it can still run legacy 16-bit real mode code:
.model small
.386
.387
And every segment is marked with USE16
too; everything else in this program works just fine btw
Also, I'm not exactly sure on how important this is, but the last values in the stack seem to be the same each time I call it, maybe this also has something to do with all that, I dunno:
ST(4) and ST(5) = 400A BB80 0000 0000 0000
ST(6) = FFFF 8000 0000 0000 0000
ST(7) = 7FFF 8000 0000 0000 0000
(Mini-UPD about this: sometimes these values are different too, sometimes the values in other stack registers change, I'd assume this is just leftover junk data from other programs)
So, I guess at this point I'm just kinda stuck, not even sure what to do with this?
UPD # 1: "This question needs debugging details." What debugging details? Anyway, here's the minimal sample program that just does a few FPU operations:
.model small
.386
.387
SSEG segment stack USE16
db 512 dup(?)
SSEG ends
DATA segment USE16
temp_32 dd ?
temp_16 dw ?
klfdasj db "Hello World??...$"
DATA ends
CODE segment USE16
assume cs:CODE, ds:DATA, ss:SSEG
prog:
mov dx, DATA
mov ds, dx
finit
mov eax, 105
mov temp_32, eax
fild temp_32 ; attempt # 1
fldpi ; attempt # 2
fldz ; attempt # 3
fld1 ; atttempt # 4
mov temp_16, ax
fild temp_16 ; attempt # 5
fild temp_32 ; attempt # 6, for good measure
finit
fild temp_32 ; I even tried to call finit again haha
fstp temp_32 ; By the way, seems like if I do this with an empty stack then it will read some kind of garbage value (`00 00 D2 42` in this case) which is the same each time
lea dx, klfdasj
mov ah, 9
int 21h
mov ax, 4CFFh
int 21h
CODE ends
end prog
Compiled with TASM and linked with TLINK as usual (I also needed some 32-bit stuff in my original program, but in here it doesn't work whether it's linked with the /3
flag or without)
UPD # 2: as requested, a screenshot for a minimal program with just finit
and fld1
(the ST(n) are all empty):
UPD # 3: Okay, I actually have been having this suspicion that TD is just lying to me for whatever reason. I think this could be posted as an answer to my own question (to potentially help the folks in the future) but it's for now closed, unfortunately. Anyway, I wrote this little program to test it out:
.model small
.386
.387
.STACK 200h
.DATA
thing dd 0
beep dw 105
yes db "It's working?$"
.CODE
prog:
mov ax, @DATA
mov ds, ax
finit
fld1
fistp thing
mov eax, thing
cmp eax, 1
jne @bye
fild beep
fistp thing
mov eax, thing
cmp eax, 105
jne @bye
mov ah, 9
lea dx, yes
int 21h
@bye:
mov ax, 4CFFh
int 21h
end prog
I'd presume this should: load 1 onto the FPU stack, then load it into memory, compare the memory result with 1, then do the same with loading a value from memory, and then, if both values are correct, it would print out the text on the screen; if I'm correct. And, well, it does print it out, so the FPU is probably actually working, and the issue might instead be with the debugger