A test program?

A forum for users of EhBASIC (Enhanced BASIC), a portable BASIC interpreter for 6502 microcomputers written by Lee Davison.
User avatar
dclxvi
Posts: 362
Joined: 11 Mar 2004

Re: A test program?

Post by dclxvi »

The atan2 calculation in line 50 uses X<0, but the sign of TRUE turns out not to matter in that case because the comparison in line 60 is mod pi.

The argument for TRUE = 1 is that it's slightly easier to pack into (and unpack from) a bitfield or an array of bits. The argument for -1 is that it's more useful with bitwise operators (including XOR). I'm more of a fan of -1 myself, but both arguments are reasonable. (Apple I BASIC and Apple "Integer" BASIC also use 1.)

Also, it might be useful to have at least (tested versions of) some of these examples in source code repository and/or possibly a link to this thread. Adding a link to the EhBASIC link in on the homebuilt projects page might also be helpful.
User avatar
BillO
Posts: 1038
Joined: 12 Dec 2008
Location: Canada

Re: A test program?

Post by BillO »

floobydust wrote:
... but retirement has gotten overly busy, who knew :roll:
:lol:

My very same lament. :roll:

Not only did I get myself involved in a full time 'career' playing trombone in 5 bands, and increasing my efforts in my digital electronics hobby, but also agreed to help my wife re-build a run-down cottage to use as an income property. We think we can control our type 'A' personalities, but in fact, they are what we are... :!: :cry: :? :shock:
Bill
User avatar
BigEd
Posts: 11464
Joined: 11 Dec 2008
Location: England
Contact:

Re: A test program?

Post by BigEd »

dclxvi wrote:
The argument for TRUE = 1 is that it's slightly easier to pack into (and unpack from) a bitfield or an array of bits. The argument for -1 is that it's more useful with bitwise operators (including XOR).
I always liked the approach taken in BBC Basic. The Boolean value of an expression is the same as testing for non-zero. That is, zero is false and non-zero is true. The builtin FALSE has the value zero, and the builtin TRUE has the value -1. As a consequence of all that, the boolean and bitwise operators are the same things and act in the expected way. It's even the case that NOT TRUE is equal to FALSE and NOT FALSE is equal to TRUE.
Klaus2m5
Posts: 442
Joined: 28 Jul 2012
Location: Wiesbaden, Germany

Re: A test program?

Post by Klaus2m5 »

BigEd wrote:
I always liked the approach taken in BBC Basic. The Boolean value of an expression is the same as testing for non-zero. That is, zero is false and non-zero is true.
I am not aware of any Basic that does not support this. You can replace

Code: Select all

X = 5 : REM any value other than 0
IF X <> 0 THEN
by

Code: Select all

X = 5 : REM any value other than 0
IF X THEN
6502 sources on GitHub: https://github.com/Klaus2m5
User avatar
GaBuZoMeu
Posts: 660
Joined: 01 Mar 2017
Location: North-Germany

Re: A test program?

Post by GaBuZoMeu »

Chromatix wrote:
Quote:
3. 1 4 1 5 9 2 6 5 3 5 8 9 7 9 3 2 3 8 4 6 2 6 4 3 3 8 3 2 7 9
You can improve the formatting of this by changing "PRINT Q;" to "PRINT ;Q;".
EhBasic seems to be different on that. "PRINT ;Q;" wouldn't work:

Code: Select all

190 ?;Q;
RUN
 3. 1 4 1 5 9 2 6 5 3 5 8 9 7 9 3 2 3 8 4 6 2 6 4 3 3 8 3 2 7 9
Ready
190 ?CHR$(Q+48);
RUN
3.141592653589793238462643383279
Ready
The hard way does ;)
Klaus2m5
Posts: 442
Joined: 28 Jul 2012
Location: Wiesbaden, Germany

Re: A test program?

Post by Klaus2m5 »

The string compare is at LAB_1CAE. At LAB_1CE6 the strings are actually compared if they have the same length. FAC1_1 and FAC2_2 is used to hold the indirect pointer to the strings being compared. FAC2_2 was pointing to an invalid location in direct mode. Earlier in the code the string descriptor is pulled

Code: Select all

      LDA   FAC2_2            ; get descriptor pointer low byte
      LDY   FAC2_3            ; get descriptor pointer high byte
      JSR   LAB_22BA          ; pop (YA) descriptor off stack or from top of string space
                              ; returns with A = length, X=pointer low byte,
                              ; Y=pointer high byte
      STX   FAC2_2            ; save string pointer low byte
      STY   FAC2_3            ; save string pointer high byte
In memory the pointer to the string descriptor is off by +$100. So I went back to LAB_EVEX to see where FAC2_2 is loaded. After some more single stepping I found it is pushed onto the stack from FAC1 and then restored to FAC2. When it is pushed to the stack via LAB_1B5B FAC1 is rounded which causes the high address to be incremented by 1 if FAC1_r is > $7f. FAC1_r is not cleared when FAC1 actually contains a memory pointer. Actually it is never cleared and so I am not so sure wether it could also go wrong in run mode.

Code: Select all

; push sign, round FAC1 and put on stack

LAB_1B5B
      PLA                     ; get return addr low byte
      STA   ut1_pl            ; save it
      INC   ut1_pl            ; increment it (was ret-1 pushed? yes!)
                              ; note! no check is made on the high byte! if the calling
                              ; routine assembles to a page edge then this all goes
                              ; horribly wrong !!!
      PLA                     ; get return addr high byte
      STA   ut1_ph            ; save it
      LDA   FAC1_s            ; get FAC1 sign (b7)
      PHA                     ; push sign

; round FAC1 and put on stack

LAB_1B66
      JSR   LAB_27BA          ; round FAC1
      LDA   FAC1_3            ; get FAC1 mantissa3
      PHA                     ; push on stack
      LDA   FAC1_2            ; get FAC1 mantissa2
      PHA                     ; push on stack
      LDA   FAC1_1            ; get FAC1 mantissa1
      PHA                     ; push on stack
      LDA   FAC1_e            ; get FAC1 exponent
      PHA                     ; push on stack
      JMP   (ut1_pl)          ; return, sort of
Either FAC1_r must be cleared when FAC1 is used as a memory pointer or LAB_27BA should check wether the data type is string or number (without breaking something else of course).

edit: Sorry, I have posted this in the wrong thread. I will repost to the correct one.
Last edited by Klaus2m5 on Sun Jul 01, 2018 4:47 pm, edited 1 time in total.
6502 sources on GitHub: https://github.com/Klaus2m5
JenniferDigital
Posts: 92
Joined: 25 May 2015

Re: A test program?

Post by JenniferDigital »

I wasn't expecting the FAC1 (which I thought to be a floating point accumulator) to be used as a pointer.
User avatar
barrym95838
Posts: 2056
Joined: 30 Jun 2013
Location: Sacramento, CA, USA

Re: A test program?

Post by barrym95838 »

DigitalDunc wrote:
I wasn't expecting the FAC1 (which I thought to be a floating point accumulator) to be used as a pointer.
Agreed. If there's a point to that apparent level of complexity, it whizzed past my head.

Mike B.
soci
Posts: 20
Joined: 18 Nov 2019

Re: A test program?

Post by soci »

Quick hack I did yesterday for testing. The original was for CBM PET and was adapted to use VT100 control sequences. Might be too fast on some systems with high baud rates. But is usable on my setup (~1.7Mhz and 38400N1).

Code: Select all

0 REM BASED ON ORIGINAL PETRIS (C)2002 CURTIS F KAYLOR
10 E$=CHR$(27)+"[":R$=E$+"C":U$=E$+"A":L$=E$+"D":W$=E$+"B":I$=E$+"7m":J$=E$+"27m"
20 DIMT$(15),B(6,3,3),P(23),I(2):I$(0)=R$:I$(1)="":I$(2)=L$
21 T$(0)=E$+"4C":T$(1)=E$+"3C ":T$(2)=E$+"2C "+R$:T$(3)=E$+"2C  "
22 T$(4)=R$+" "+E$+"2C":T$(5)=R$+" "+R$+" ":T$(6)=R$+"  "+R$:T$(7)=R$+"   "
23 T$(8)=" "+E$+"3C":T$(9)=" "+E$+"2C ":T$(10)=" "+R$+" "+R$:T$(11)=" "+R$+"  "
24 T$(12)="  "+E$+"2C":T$(13)="  "+R$+" ":T$(14)="   "+R$:T$(15)="    "
30 S=0:M=0:Z=0
40 B$="DDDD@O@@DDDD@O@@@FDD@GA@@AAC@DG@@FBB@AG@@DDF@GD@@BFB@BG@@BCB@GB@@ACB@FC@"
50 B$=B$+"@ACB@FC@@DFB@CF@@DFB@CF@@FF@@FF@@FF@@FF@":FORI=0TO6:FORJ=0TO3:FORK=0TO3
60 Z=Z+1:B(I,J,K)=ASC(MID$(B$,Z))AND15:NEXT:NEXT:NEXT:FORI=0TO19:P(I)=4097:NEXT
61 P(I)=8191:PRINTE$"H"E$"2J";
70 PRINTE$"H":FORI=0TO20:P=8191-P(I)
71 PRINTT$(P/4096)T$(P/256AND15)T$(P/16AND15)T$(PAND15)
72 P=8191-P:PRINTU$I$T$(P/4096)T$(P/256AND15)T$(P/16AND15)T$(PAND15)J$:NEXT
80 PRINTU$E$"4C"I$"PETRIS"S;
90 X=32:Y=0:B=7*RND(0):C=0:D=2:PRINTE$"H"E$"7C"W$;:R=1
100 IFRTHEND$="":FORI=0TO3:D$=D$+T$(B(B,C,I))+W$+E$+"4D":NEXT:D$=D$+E$+"4A"
110 PRINTI$(M+1)I$D$J$;
115 GETK$:M=(K$="2")-(K$="1"):R=K$=" ":V=M+R=0:IFK$<>""ANDVTHENGOTO115
120 IFMTHENX=X*(2.5+M*1.5)/2:GOSUB160:IFZTHENX=X*(2.5-M*1.5)/2:GOTO115
130 IFRTHENC=C-RAND3:GOSUB160:IFZTHENC=C+RAND3:GOTO115
140 IFVTHENY=Y+1:GOSUB160:IFZTHENY=Y-1:ONSGN(Y)GOTO170:END
150 PRINTD$LEFT$(W$,-V*3);:GOTO100
160 Z=0:FORI=0TO3:Z=ZOR(P(Y+I)ANDB(B,C,I)*X):NEXT:RETURN
170 A=0:FORI=0TO3:P(Y+I)=P(Y+I)ORB(B,C,I)*X:IFP(Y+I)=8191ANDY+I<20THENGOSUB190
180 NEXT:ONDGOTO70,90
190 FORZ=Y+ITO1STEP-1:P(Z)=P(Z-1):NEXT:P(0)=4097:D=1:A=A+10:S=S+A:RETURN
Post Reply