stardot / MatrixBrandy

Matrix Brandy BASIC VI for Linux, Windows, MacOSX
http://brandy.matrixnetwork.co.uk/
44 stars 8 forks source link

Program environment pseudovars break IF/THEN statements #65

Closed jgharston closed 5 years ago

jgharston commented 5 years ago

If a program pseudovar is used in an IF/THEN statement, a Type mismatch error occurs. Probably an issue from adding 64-bit integers. Could be due to an INT32/INT64 type being misinterpretated. Examples:

PRINT ~PAGE, ~TOP, ~LOMEM, ~HIMEM 1E80020 1E8151C 1E81524 1F00020 PRINT PAGE>1,TOP>1,LOMEM>1,HIMEM>1 -1 -1 -1 -1 IF PAGE>1 THEN PRINT "HELLO" Type mismatch: number wanted IF TOP>1 THEN PRINT "HELLO" Type mismatch: number wanted IF LOMEM>1 THEN PRINT "HELLO" Type mismatch: number wanted IF HIMEM>1 THEN PRINT "HELLO" Type mismatch: number wanted

And just to make sure it's not the command after the THEN:

IF PAGE>1 THEN REM Type mismatch: number wanted

Tested on and affects DJGPP, MinGW and WinSDL builds, so probably not build specific. This kills all the test programs that examine the program's environment! :(

jgharston commented 5 years ago

It's more than IF/THEN and pseudovars:

10DEFFNs(A$)=A$ 20DEFFNhost(A%)="HELLO" PRINT FNs(FNhost(0)) Type mismatch: string wanted for PROC/FN parameters

soruk42 commented 5 years ago

OK, Just checked in a fix for this. Just be aware, that especially on 32-bit builds PAGE can be negative.

jgharston commented 5 years ago

On 22-09-2019 17:51, Michael McConnell wrote:

OK, Just checked in a fix for this. Just be aware, that especially on 32-bit builds PAGE can be negative.

That will need some testing, it's a common coding method to use, eg max%=HIMEM-LOMEM-fudge:DIM mem% max%

as well as: IF HIMEM<&FFFF THEN I'm running in an 8-bit environment

and a lot of DIM'd data manipulation is going to go wrong if pointers to memory can "look" negative. Things like malloc-like code that does things like IF next%-this%<size% THEN not enough space will start falling over if next% and this% are above 2G and so look negative. And FOR/NEXTing through memory will fall over when the index variable suddenly becomes hugely negative.

It looks like one of those things where the answer to "how do I deal with grabbing more than 2G from the heap" is "if you're trying to hold more than 2G in the heap, you should be using some other method". There's probably a huge mass of code that's written on the totally natural assumption that all of BASIC's memory will be at positive memory addresses.

(I remember writing code for the CPC which used 16-bit ints, and the hassle with using memory addresses where Basic's memory went from &400-ish to &B000-ish, but from Basic's point of view that went from positive addresses to negative addresses passing from &7FFF to &8000.)

target.h probably needs a ALLOW64BIT or something so it can be sprinkled into the code to prevent builds for targets that can't cope from building the 64-bit code.

-- J.G.Harston - jgh@mdfs.net - mdfs.net/jgh

soruk42 commented 5 years ago

I've pushed a further update, that ensures that, since PAGE et al all now return 64-bit integers, that on 32-bit platforms the top 32 bits are unset, so they now return positive integers.

A side-effect of this is, if PAGE > &7FFFFFFF then you can't store it in a 32-bit integer variable.