├── examples ├── Snow ├── cricket ├── shroud ├── sphere ├── spiral-pattern ├── Mode7 │ ├── README │ ├── SAA505xDemo │ ├── m7point │ └── M7terminal ├── sierpinski ├── sine ├── pastriang ├── mouse-doodle ├── splash ├── cmdline ├── tekdemo1 ├── hanoi ├── sieve ├── spiral ├── tekspiral ├── bin2c ├── graphdemo ├── dow ├── tekdemo2 ├── BubbleUniverse ├── testArcSectorSegment ├── trees1 ├── trees2 ├── gpiolib ├── README ├── combsort ├── lands ├── testEllipse ├── teklib ├── SAA505Xlib ├── hex └── platformcheck ├── tests ├── Circle ├── ClockSp ├── Colours ├── DefChar ├── Environ ├── EscTest ├── KBDTest ├── KeyScan ├── KeyTest ├── ANSIColour ├── ColourANSI ├── ColourGrid ├── Graphics ├── KeyDOS ├── KeySDL └── notes ├── src ├── textfonts.h ├── soundsdl.h ├── commands.h ├── lvalue.h ├── convert.h ├── assign.h ├── net.h ├── variables.h ├── evaluate.h ├── strings.h ├── heap.h ├── statement.h ├── editor.h ├── functions.h ├── fileio.h ├── iostate.h ├── keyboard.h ├── mainstate.h ├── miscprocs.h ├── mos.h ├── graphsdl.h └── common.h ├── desktop ├── brandy.png ├── telstar ├── telstar.png ├── telstar.desktop └── brandy.desktop ├── other-makefiles ├── README ├── makefile.djgpp ├── makefile.mingw ├── makefile.riscos └── makefile.riscos.gcc ├── Dockerfile.sbrandy ├── t └── 01count.t ├── .gitignore ├── docs ├── standalone-app.txt ├── networking.txt ├── RISC-OS.txt ├── identification.txt ├── README ├── keyboard-codes ├── banana-bugs.txt ├── raspi-gpio.txt ├── graphics.txt ├── jgh-notes.txt ├── Mode7.txt ├── Config.txt ├── keymap.txt ├── osbyte.txt ├── extensions.txt ├── ScreenModes.txt └── compiling.txt ├── READ.ME ├── makefile.app ├── makefile.text ├── makefile ├── makefile.mingw-sdl ├── makefile.app.mingw-sdl ├── makefile.mingw-text ├── CMakeLists.txt ├── .github └── workflows │ └── actions.yml └── MatrixBrandy.spec /examples/Snow: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/examples/Snow -------------------------------------------------------------------------------- /tests/Circle: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/tests/Circle -------------------------------------------------------------------------------- /tests/ClockSp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/tests/ClockSp -------------------------------------------------------------------------------- /tests/Colours: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/tests/Colours -------------------------------------------------------------------------------- /tests/DefChar: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/tests/DefChar -------------------------------------------------------------------------------- /tests/Environ: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/tests/Environ -------------------------------------------------------------------------------- /tests/EscTest: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/tests/EscTest -------------------------------------------------------------------------------- /tests/KBDTest: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/tests/KBDTest -------------------------------------------------------------------------------- /tests/KeyScan: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/tests/KeyScan -------------------------------------------------------------------------------- /tests/KeyTest: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/tests/KeyTest -------------------------------------------------------------------------------- /examples/cricket: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/examples/cricket -------------------------------------------------------------------------------- /examples/shroud: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/examples/shroud -------------------------------------------------------------------------------- /src/textfonts.h: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/src/textfonts.h -------------------------------------------------------------------------------- /tests/ANSIColour: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/tests/ANSIColour -------------------------------------------------------------------------------- /tests/ColourANSI: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/tests/ColourANSI -------------------------------------------------------------------------------- /tests/ColourGrid: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/tests/ColourGrid -------------------------------------------------------------------------------- /tests/Graphics: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/tests/Graphics -------------------------------------------------------------------------------- /desktop/brandy.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/desktop/brandy.png -------------------------------------------------------------------------------- /other-makefiles/README: -------------------------------------------------------------------------------- 1 | These makefiles are untested - I don't have the means to test. 2 | -------------------------------------------------------------------------------- /desktop/telstar: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | exec brandy $(rpm -ql brandy-examples | grep Mode7/telstar) 3 | -------------------------------------------------------------------------------- /desktop/telstar.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stardot/MatrixBrandy/HEAD/desktop/telstar.png -------------------------------------------------------------------------------- /desktop/telstar.desktop: -------------------------------------------------------------------------------- 1 | [Desktop Entry] 2 | Encoding=UTF-8 3 | Name=Telstar 4 | Exec=/usr/bin/telstar 5 | Icon=/usr/share/pixmaps/telstar.png 6 | Type=Application 7 | Categories=Network; 8 | -------------------------------------------------------------------------------- /desktop/brandy.desktop: -------------------------------------------------------------------------------- 1 | [Desktop Entry] 2 | Encoding=UTF-8 3 | Name=Matrix Brandy 4 | Exec=/usr/bin/brandy 5 | Icon=/usr/share/pixmaps/brandy.png 6 | Type=Application 7 | Categories=Development; 8 | -------------------------------------------------------------------------------- /examples/sphere: -------------------------------------------------------------------------------- 1 | 10 SYS "Brandy_TekEnabled",1, 115200 2 | 20 VDU5:CLG 3 | 30 S%=400 4 | 40 VDU29,640;512; 5 | 50 MOVE 0,0 6 | 60 FOR A=0 TO 126 STEP .125: DRAW S%*SINA,S%*COSA*SIN(A*.95):NEXT 7 | 70 VDU4 8 | -------------------------------------------------------------------------------- /examples/spiral-pattern: -------------------------------------------------------------------------------- 1 | 10SYS"Brandy_TekEnabled",1,115200 2 | 30VDU5:CLG 3 | 40VDU 29,640;512; 4 | 50TIME=0:FOR I=1 TO 1000 STEP 2.4 5 | 60D=16*SQRI:MOVE D*COSI,D*SINI:POINT D*COSI,D*SINI 6 | 70NEXT 7 | 80VDU 4 8 | -------------------------------------------------------------------------------- /Dockerfile.sbrandy: -------------------------------------------------------------------------------- 1 | FROM debian:12 AS build 2 | RUN apt-get update && apt-get install -y build-essential cmake 3 | COPY . /build 4 | WORKDIR /build 5 | RUN cmake . 6 | RUN cmake --build . 7 | RUN ctest 8 | 9 | FROM debian:12 10 | COPY --from=build /build/sbrandy /usr/local/bin/sbrandy 11 | ENTRYPOINT ["/usr/local/bin/sbrandy"] 12 | -------------------------------------------------------------------------------- /tests/KeyDOS: -------------------------------------------------------------------------------- 1 | 10 REM > KeyDOS 2 | 20 CLS 3 | 30 OFF 4 | 40 REPEAT 5 | 50 VDU 30 6 | 60 FOR A%=0 TO 255 7 | 70 IF INKEY(&FE00+A%):PRINT" "FNh0(A%,3); ELSE PRINTSPC4; 8 | 80 IF (A% AND 15)=15:PRINT 9 | 90 NEXT 10 | 100 UNTIL FALSE 11 | 110 DEFFNh0(A%,N%)=RIGHT$("0000000"+STR$~A%,N%) 12 | -------------------------------------------------------------------------------- /tests/KeySDL: -------------------------------------------------------------------------------- 1 | 10 REM > KeySDL 2 | 20 CLS 3 | 30 OFF 4 | 40 REPEAT 5 | 50 VDU 30 6 | 60 FOR A%=0 TO 510 7 | 70 IF INKEY(&FC00+A%):PRINT" "FNh0(A%,3); ELSE PRINTSPC4; 8 | 80 IF (A% AND 15)=15:PRINT 9 | 90 NEXT 10 | 100 UNTIL FALSE 11 | 110 DEFFNh0(A%,N%)=RIGHT$("0000000"+STR$~A%,N%) 12 | -------------------------------------------------------------------------------- /examples/Mode7/README: -------------------------------------------------------------------------------- 1 | Here are some examples for Mode 7. 2 | 3 | mode7demo is a selection of Teletext pages including the Ceefax 4 | Engineering Test page. 5 | 6 | telstar is a Brandy BASIC Telstar client, demonstrating both the Mode 7 7 | capability and the network connectivity feature added in V1.21.6 8 | 9 | ttxtedit is a simple Teletext screen editor. 10 | -------------------------------------------------------------------------------- /t/01count.t: -------------------------------------------------------------------------------- 1 | #!sbrandy 2 | REM https://testanything.org/ 3 | PRINT "1..3" 4 | 5 | Colour% = 1 6 | Pi = 0 7 | 8 | FOR I% = 0 TO 10 9 | Colour% += I% 10 | Pi += I% 11 | NEXT 12 | 13 | REM Assertions 14 | IF Colour% = 56 THEN PRINT "ok 1" ELSE PRINT "not ok 1" 15 | IF Pi = 55 THEN PRINT "ok 2" ELSE PRINT "not ok 2" 16 | IF Colour% - Pi = 1 THEN PRINT "ok 3" ELSE PRINT "not ok 3" 17 | -------------------------------------------------------------------------------- /examples/sierpinski: -------------------------------------------------------------------------------- 1 | 10ONERRORVDU4:END 2 | 20SYS "Brandy_TekEnabled",1,115200 3 | 30MODE 74 4 | 40VDU5:CLG 5 | 50DIM X%(3),Y%(3) 6 | 60X%(1)=32:Y%(1)=32 7 | 70X%(2)=2016:Y%(2)=32 8 | 80X%(3)=1024:Y%(3)=1528 9 | 90X%=RND(2048):Y%=RND(1560) 10 | 100REPEAT 11 | 110N%=RND(3) 12 | 120X% = (X%+X%(N%))/2 : Y% = (Y%+Y%(N%))/2 13 | 130PLOT 69,X%,Y% 14 | 140UNTIL FALSE 15 | -------------------------------------------------------------------------------- /examples/sine: -------------------------------------------------------------------------------- 1 | REM This program works either in the SDL build of Matrix Brandy, or 2 | REM the full text mode version (tbrandy) when run from an xterm window. 3 | : 4 | SYS "Brandy_TekEnabled",1 5 | MODE 20 6 | VDU5:CLG 7 | x%=0 8 | ORIGIN 0, 512 9 | LINE 0, 0, 1279, 0 10 | LINE 0, -480, 0, 480 11 | MOVE 0,0 12 | FOR angle=0 TO 2*PI STEP PI/50 13 | DRAW x%, 480*SIN(angle) 14 | x%+=12 15 | NEXT 16 | VDU4 17 | END 18 | -------------------------------------------------------------------------------- /examples/pastriang: -------------------------------------------------------------------------------- 1 | REM this program draws Pascal's triangle 2 | 3 | SIZE% = 12 4 | DIM prev%(SIZE%), next%(SIZE%) 5 | next%() = 0 6 | next%(0) = 1 7 | FOR I%=0 TO SIZE%-1 8 | PRINT TAB(35-3*I%);next%(0); 9 | IF I%>0 THEN 10 | FOR J%=1 TO I% 11 | next%(J%) = prev%(J%)+prev%(J%-1) 12 | PRINT RIGHT$(" "+STR$next%(J%), 6); 13 | NEXT 14 | ENDIF 15 | PRINT 16 | prev%() = next%() 17 | NEXT 18 | END 19 | -------------------------------------------------------------------------------- /examples/mouse-doodle: -------------------------------------------------------------------------------- 1 | 10REM>mouse-doodle 2 | 20MODE 13 3 | 30OFF 4 | 40GCOL0,RND(63) 5 | 50T%=0 6 | 60REPEAT 7 | 70MOUSE X%, Y%, B% 8 | 80IF B% = 7 THEN ON:END 9 | 90IF B% = 6 THEN CLS: GOTO 70 10 | 100IF (B% AND 4) OR T%=1 THEN DRAW X%,Y% ELSE MOVE X%,Y% 11 | 110IF B% AND 1 THEN GCOL0,RND(63) 12 | 120IF B% = 2 THEN T%=T% EOR 1: REPEAT: MOUSE A, B, C: UNTIL C=0 13 | 130WAIT 1 14 | 140UNTIL 0 15 | -------------------------------------------------------------------------------- /examples/splash: -------------------------------------------------------------------------------- 1 | 10SYS "Brandy_TekEnabled",1,115200 2 | 20MODE 74 3 | 30VDU5:CLG 4 | 40S%=8 5 | 50ORIGIN 1024,780 6 | 60FOR X%=-1024 TO 0 STEP 2 7 | 70M%=-780 8 | 80FOR Y%=-1212 TO 1400 STEP S% 9 | 90V%=(Y%+FNA(X%,Y%))/2 10 | 100IF M% SAA505xDemo 2 | 20LIBRARY "../SAA505Xlib" 3 | 30MODE 7 4 | 40VDU23,18,3,1|:OFF 5 | 50PRINT" Primary:" 6 | 60FOR x% = 0 TO 7 7 | 70VDU &20 8 | 80FOR y% = 160 TO 255 STEP 8 9 | 90VDUx%+y%,32 10 | 100NEXT y%:PRINT 11 | 110NEXT x% 12 | 120PRINT:PRINT CHR$(&9B);"Secondary:" 13 | 130FOR x% = 0 TO 7 14 | 140VDU &9B 15 | 150FOR y% = 160 TO 255 STEP 8 16 | 160VDUx%+y%,32 17 | 170NEXT y%:PRINT 18 | 180NEXT x% 19 | 190N%=0 20 | 200REPEAT 21 | 210PRINTTAB(0,20)"SAA505";N% 22 | 230PROCsaa505xlibset(N%,1) 23 | 240WAIT200 24 | 250N%+=1 25 | 260IFN%=8THENN%=0 26 | 270UNTILN%=0 27 | 280ON 28 | -------------------------------------------------------------------------------- /examples/tekspiral: -------------------------------------------------------------------------------- 1 | REM NOTE: This program will ONLY run in an xterm window under NetBSD and Linux. 2 | REM 3 | REM It uses the Tektronics graphics terminal emulation that xterm provides 4 | REM to draw a simple graph in the xterm 'Tek' window. 5 | : 6 | LIBRARY"examples/teklib" 7 | PROCtekinit 8 | PROCmode(0) 9 | R%=2500 10 | H%=R%/2 11 | REM rotated towards viewer by: 12 | R=-PI/4 13 | U=COS(R):V=SIN(R) 14 | PROCP(4,0) 15 | FORI%=1TOR% 16 | PROCP(5,I%) 17 | NEXT 18 | PROCtekexit 19 | END 20 | DEFPROCP(C%,S%) 21 | T=PI*(S%-H%)/R% 22 | C=COS(T) 23 | X=COS(50*T)*C 24 | Z=SIN(50*T)*C 25 | Y=SIN(T) 26 | W=Y*U+Z*V 27 | Z=-Y*V+Z*U 28 | Y=W 29 | P=3500/(8-Z) 30 | IFC%=4 THEN PROCmove(1024+X*P,768+Y*P) ELSE PROCdraw(1024+X*P,768+Y*P) 31 | ENDPROC 32 | -------------------------------------------------------------------------------- /src/soundsdl.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Brandy Basic VI Interpreter. 3 | ** soundsdl.h by David Hawes. 4 | ** 5 | */ 6 | 7 | #ifndef SOUND_SDL_H_INC 8 | 9 | #define SOUND_SDL_H_INC 10 | 11 | extern void init_sound(void); 12 | 13 | extern void sdl_sound(int32, int32, int32, int32, int32); 14 | extern void sdl_sound_onoff(int32); 15 | 16 | extern void sdl_wrbeat(int32); 17 | extern int32 sdl_rdbeat(void); 18 | extern int32 sdl_rdbeats(void); 19 | extern void sdl_wrtempo(int32); 20 | extern int32 sdl_rdtempo(void); 21 | extern void sdl_voice(int32, char *); 22 | extern void sdl_voices(int32); 23 | extern void sdl_star_voices(void); 24 | extern void sdl_stereo(int32, int32); 25 | extern void sdl_volume(int32); 26 | 27 | #endif 28 | -------------------------------------------------------------------------------- /examples/bin2c: -------------------------------------------------------------------------------- 1 | 10ON ERROR IF ERR=26 THEN GOTO 300 ELSE REPORT: PRINT " at line ";ERL:END 2 | 20IF ARGC < 2 THEN GOTO 300 3 | 30infile$=ARGV$(1) 4 | 40outfile$=ARGV$(2) 5 | 50i%=OPENIN(infile$) 6 | 60o%=OPENOUT(outfile$) 7 | 70l%=0 8 | 80BPUT#o%,"const char _binary_app_start[] = { " 9 | 90WHILE EOF#i%=0 10 | 100 c%=BGET#i% 11 | 110 BPUT#o%,STR$c%+","; 12 | 120 l%+=1 13 | 130ENDWHILE 14 | 140PTR#o%=(PTR#o%-1) 15 | 150BPUT#o%,"" 16 | 160BPUT#o%,"};" 17 | 170BPUT#o%,"const int _binary_app_len="+STR$l%+";" 18 | 180CLOSE#i% 19 | 190CLOSE#o% 20 | 200END 21 | 300REM ARM BBC BASIC handler, also used if no CLI parameters given in Brandy 22 | 310INPUT "Input filename >"infile$ 23 | 320INPUT "Output filename >"outfile$ 24 | 330GOTO 50 25 | -------------------------------------------------------------------------------- /examples/graphdemo: -------------------------------------------------------------------------------- 1 | REM This program works either in the SDL build of Matrix Brandy, or 2 | REM the full text mode version (tbrandy) when run from an xterm window. 3 | : 4 | SYS "Brandy_TekEnabled", 1 5 | MODE 27 6 | VDU5:CLG 7 | ORIGIN 640, 512 8 | xlow = -10 9 | xhigh = 10 10 | ylow = -10 11 | yhigh = 10 12 | depth = 10 13 | xscale = 30 14 | yscale = 12 15 | c = -4000 16 | : 17 | FOR x = xlow TO xhigh 18 | MOVE xscale*(x+ylow), yscale*(ylow-x)+c/(x*x+ylow*ylow+depth) 19 | FOR y = ylow TO yhigh 20 | DRAW xscale*(x+y), yscale*(y-x)+c/(x*x+y*y+depth) 21 | NEXT 22 | NEXT 23 | FOR y = ylow TO yhigh 24 | MOVE xscale*(xlow+y), yscale*(y-xlow)+c/(xlow*xlow+y*y+depth) 25 | FOR x = xlow TO xhigh 26 | DRAW xscale*(x+y), yscale*(y-x)+c/(x*x+y*y+depth) 27 | NEXT 28 | NEXT 29 | VDU4 30 | END 31 | -------------------------------------------------------------------------------- /examples/dow: -------------------------------------------------------------------------------- 1 | DIM month$(12) 2 | month$()="", "January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December" 3 | REPEAT 4 | INPUT"Enter date in the form dd,mm,yy: " dd%, mm%, yy% 5 | UNTIL dd%>=1 AND dd%<=31 AND mm%>=1 AND mm%<=12 6 | IF yy%<=99 THEN 7 | IF yy%<70 THEN yy%+=2000 ELSE yy%+=1900 8 | ENDIF 9 | IF mm%<3 THEN 10 | factor=365*yy%+dd%+31*(mm%-1)+(yy%-1) DIV 4-INT(0.75*INT(((yy%-1)/100)+1)) 11 | ELSE 12 | factor=365*yy%+dd%+31*(mm%-1)-INT(0.4*mm%+2.3)+INT(yy%/4)-INT(0.75*(yy% DIV 100+1)) 13 | ENDIF 14 | dow%=factor-factor DIV 7*7 15 | PRINT month$(mm%);" ";dd%;", ";yy%;" is a "; 16 | CASE dow% OF 17 | WHEN 0: PRINT"Saturday" 18 | WHEN 1: PRINT"Sunday" 19 | WHEN 2: PRINT"Monday" 20 | WHEN 3: PRINT"Tuesday" 21 | WHEN 4: PRINT"Wednesday" 22 | WHEN 5: PRINT"Thursday" 23 | WHEN 6: PRINT"Friday" 24 | ENDCASE 25 | END 26 | 27 | -------------------------------------------------------------------------------- /examples/tekdemo2: -------------------------------------------------------------------------------- 1 | REM NOTE: This program will ONLY run in an xterm window under NetBSD and Linux. 2 | REM 3 | REM It uses the Tektronics graphics terminal emulation that xterm provides 4 | REM to draw a simple graph in the xterm 'Tek' window. 5 | : 6 | LIBRARY"examples/teklib" 7 | PROCtekinit 8 | PROCmode(0) 9 | PROCorigin(1024, 750) 10 | xlow = -10 11 | xhigh = 10 12 | ylow = -10 13 | yhigh = 10 14 | depth = 8 15 | xscale = 50 16 | yscale = 20 17 | c = -4000 18 | : 19 | FOR x = xlow TO xhigh 20 | PROCmove(xscale*(x+ylow), yscale*(ylow-x)+c/(x*x+ylow*ylow+depth)) 21 | FOR y = ylow TO yhigh 22 | PROCdraw(xscale*(x+y), yscale*(y-x)+c/(x*x+y*y+depth)) 23 | NEXT 24 | NEXT 25 | FOR y = ylow TO yhigh 26 | PROCmove(xscale*(xlow+y), yscale*(y-xlow)+c/(xlow*xlow+y*y+depth)) 27 | FOR x = xlow TO xhigh 28 | PROCdraw(xscale*(x+y), yscale*(y-x)+c/(x*x+y*y+depth)) 29 | NEXT 30 | NEXT 31 | PROCtekexit 32 | END 33 | -------------------------------------------------------------------------------- /examples/BubbleUniverse: -------------------------------------------------------------------------------- 1 | 10ON ERROR PROCexit 2 | 20n=200 3 | 30@%=&20808 4 | 40r=PI*2/235 5 | 50V%=0 6 | 60MODE 640,512,32 7 | 70MODE 640,512,16 8 | 80x=0:y=0:v=0:t=0.22 9 | 90s=240 10 | 100OFF 11 | 110VDU 29,640;512; 12 | 120TIME=0 13 | 130frame_counter%=0 14 | 140REPEAT 15 | 150PROCtoggle 16 | 160CLS 17 | 170FOR i=0 TO n STEP 2 18 | 180FOR j=0 TO n STEP 2 19 | 190u=SIN(i+v)+SIN(r*i+x) 20 | 200v=COS(i+v)+COS(r*i+x) 21 | 210x=u+t 22 | 220r%=(i/200+0.5) MOD 2 23 | 230g%=(j/200+0.5) MOD 2 24 | 240c%=r%+g%*2 25 | 250IF c%=0 c%=4 26 | 260GCOL i+50,j+50,149 27 | 270PLOT 69,u*s,v*s 28 | 280NEXT j 29 | 290NEXT i 30 | 300t=t+0.025 31 | 310frame_counter%=frame_counter%+1 32 | 320PRINT"fps:";(frame_counter%/TIME*100) 33 | 330UNTIL 0 34 | 340DEF PROCtoggle 35 | 350V%=(V%+1)MOD 2 36 | 360SYS 6,112,V%+1 37 | 370SYS 6,113,((V%+1)MOD 2)+1 38 | 380ENDPROC 39 | 390DEF PROCexit 40 | 400SYS 6,113,V%+1 41 | 410ON 42 | 420END 43 | -------------------------------------------------------------------------------- /examples/testArcSectorSegment: -------------------------------------------------------------------------------- 1 | 10REM >TestArcSectorSegment 2 | 20MODE 0 3 | 30ORIGIN 640,512 4 | 40SX%=-34:SY%=-200 5 | 50OX%=0:OY%=0:OB%=0 6 | 60MOUSE ON 7 | 70REPEAT 8 | 80MOUSE X%,Y%,B% 9 | 90IF X%<>OX% OR Y%<>OY% OR B%<>OB% THEN 10 | 100CLS 11 | 110PRINT"Left Sector and arc start and end angles should match." 12 | 120PRINT"Right Segment and arc start and end angles should match." 13 | 130PRINT"Drag mouse to move start angle and radius" 14 | 140MOVE -240,0 15 | 150DRAW -240+SX%, SY% 16 | 160IF B%<>0 SX%=X%-240:SY%=Y%-0 17 | 170PLOT &A5,X%,Y%:REM arc 18 | 180DRAW -240,0 19 | 190MOVE -240,0 20 | 200DRAW -240+SX%*0.8, SY%*0.8 21 | 210PLOT &B5,X%,Y%:REM sector 22 | 220 23 | 230MOVE 240,0 24 | 240MOVE 240+SX%*0.8, SY%*0.8 25 | 250PLOT &AD,X%+240,Y% :REM segment 26 | 260MOVE 240,0:MOVE 240+SX%, SY%:PLOT &A5,X%+240,Y%:REM arc 27 | 270LINE 240,0,240+SX%,SY%:LINE 240,0,240+X%,Y% 28 | 280OX%=X%:OY%=Y%:OB%=B% 29 | 290WAIT 30 | 300ENDIF 31 | 310WAIT 32 | 320UNTIL FALSE 33 | -------------------------------------------------------------------------------- /examples/trees1: -------------------------------------------------------------------------------- 1 | REM Example program to create a binary tree and display 2 | REM its contents in alphabetical order of the name 3 | : 4 | DIM name$(100),value%(100),left%(100),right%(100) 5 | next%=1 6 | root%=0 7 | FOR N%=1 TO 10 8 | READ X$,X% 9 | PROCadd(X$,X%) 10 | NEXT 11 | PROCshow(root%) 12 | END 13 | : 14 | DATA red, 5, green, 10, yellow, 15, blue, 20, black, 25, white, 30 15 | DATA orange, 35, pink, 40, cyan, 45, purple, 50 16 | : 17 | : 18 | DEF PROCadd(name$,value%) 19 | name$(next%)=name$ 20 | value%(next%)=value% 21 | left%(next%)=0 22 | right%(next%)=0 23 | IF root%=0 THEN root%=1: next%=2: ENDPROC 24 | P%=root% 25 | done%=FALSE 26 | REPEAT 27 | IF name$0 THEN P%=left%(P%) ELSE left%(P%)=next%: done%=TRUE 29 | ELSE 30 | IF right%(P%)<>0 THEN P%=right%(P%) ELSE right%(P%)=next%: done%=TRUE 31 | ENDIF 32 | UNTIL done% 33 | next%+=1 34 | ENDPROC 35 | : 36 | : 37 | DEF PROCshow(P%) 38 | IF left%(P%)<>0 THEN PROCshow(left%(P%)) 39 | PRINT name$(P%);TAB(20);value%(P%) 40 | IF right%(P%)<>0 THEN PROCshow(right%(P%)) 41 | ENDPROC 42 | -------------------------------------------------------------------------------- /docs/standalone-app.txt: -------------------------------------------------------------------------------- 1 | Building standalone applications written in BASIC with Brandy 2 | ============================================================= 3 | 4 | Before you begin, note that the application will exit as soon as the BASIC 5 | program exits, as if -quit were supplied on the command line for Brandy 6 | (or *BASIC in RISC OS). 7 | 8 | This build process is in two stages. First, we build the .c file containing 9 | the program to be included: 10 | 11 | 1: Ensure you have a regular build of brandy (SD or text) built. 12 | 13 | 2: Build the file (assumes you're in the top of the repo tree): 14 | brandy examples/bin2c /path/to/basic/file src/app.c 15 | 16 | 3: The resulting app.c file is written into the src directory. (The git tree 17 | is configured to ignore this file.) 18 | 19 | Secondly, we build it: 20 | 21 | 1: Ensure the build area is clean: 22 | make -f makefile.app clean 23 | 24 | 2: Build the app binary: 25 | make -f makefile.app 26 | 27 | 3: Put the brandyapp wherever you want (usually somewhere in your $PATH), 28 | renaming it to what you want to call your app.. 29 | -------------------------------------------------------------------------------- /docs/networking.txt: -------------------------------------------------------------------------------- 1 | Networking has been added to Brandy BASIC as of version 1.21.6, significant 2 | bugs fixed for 1.21.7, and IPv6 capability added for 1.21.8. 3 | 4 | The interface is as such: 5 | 6 | Open a file handle using OPENUP, instead of a filename use "ip0:host:port", 7 | "ip4:host:port" or "ip6:host:port". When using "ip0" it'll use whichever 8 | is available, ip4 and ip6 request the connection to use only that protocol. 9 | 10 | PRINT# and INPUT# are NOT implemented for this, for a BBC BASIC internal 11 | format these are rather pointless for communicating with anything else. 12 | 13 | BGET# returns the next byte in the buffer, or -1 if no data waiting. 14 | (This is NOT an error condition, an interactive service like Telstar will 15 | not send data when it doesn't need to.) If the remote host has closed the 16 | connection, it will return -2 once the receive buffer is exhausted. 17 | 18 | GET$# returns a line of text up to the next newline. 19 | 20 | BPUT# allows bytes or strings to be sent. 21 | 22 | CLOSE# closes the network channel. This should be done even if the remote 23 | host has closed the connection. 24 | -------------------------------------------------------------------------------- /src/commands.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Matrix Brandy Basic VI Interpreter. 3 | ** Copyright (C) 2000-2014 David Daniels 4 | ** Copyright (C) 2018-2024 Michael McConnell and contributors 5 | ** 6 | ** Brandy is free software; you can redistribute it and/or modify 7 | ** it under the terms of the GNU General Public License as published by 8 | ** the Free Software Foundation; either version 2, or (at your option) 9 | ** any later version. 10 | ** 11 | ** Brandy is distributed in the hope that it will be useful, 12 | ** but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | ** GNU General Public License for more details. 15 | ** 16 | ** You should have received a copy of the GNU General Public License 17 | ** along with Brandy; see the file COPYING. If not, write to 18 | ** the Free Software Foundation, 59 Temple Place - Suite 330, 19 | ** Boston, MA 02111-1307, USA. 20 | ** 21 | ** 22 | ** This file defines the 'immediate' command functions 23 | */ 24 | 25 | #ifndef __commands_h 26 | #define __commands_h 27 | 28 | extern void exec_command(void); 29 | extern void init_commands(void); 30 | 31 | #endif 32 | -------------------------------------------------------------------------------- /src/lvalue.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Matrix Brandy Basic VI Interpreter. 3 | ** Copyright (C) 2000-2014 David Daniels 4 | ** Copyright (C) 2018-2024 Michael McConnell and contributors 5 | ** 6 | ** Brandy is free software; you can redistribute it and/or modify 7 | ** it under the terms of the GNU General Public License as published by 8 | ** the Free Software Foundation; either version 2, or (at your option) 9 | ** any later version. 10 | ** 11 | ** Brandy is distributed in the hope that it will be useful, 12 | ** but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | ** GNU General Public License for more details. 15 | ** 16 | ** You should have received a copy of the GNU General Public License 17 | ** along with Brandy; see the file COPYING. If not, write to 18 | ** the Free Software Foundation, 59 Temple Place - Suite 330, 19 | ** Boston, MA 02111-1307, USA. 20 | ** 21 | ** 22 | ** This file defines functions for dealing with lvalues 23 | */ 24 | 25 | #ifndef __lvalue_h 26 | #define __lvalue_h 27 | 28 | #include "common.h" 29 | #include "basicdefs.h" 30 | 31 | extern void get_lvalue(lvalue *); 32 | 33 | #endif 34 | -------------------------------------------------------------------------------- /examples/trees2: -------------------------------------------------------------------------------- 1 | REM Example program to create a binary tree and display 2 | REM its contents in alphabetical order of the name. 3 | REM This is the same as 'trees1' but it uses indirection 4 | REM operators 5 | : 6 | DIM heap% 1000 7 | heaptop% = heap% 8 | : 9 | REM 'struct' for a tree entry 10 | name%=0: value%=20: left%=24: right%=28: nodesize%=32 11 | root% = 0 12 | : 13 | FOR N%=1 TO 10 14 | READ X$, X% 15 | PROCadd(X$, X%) 16 | NEXT 17 | PROCshow(root%) 18 | END 19 | : 20 | DATA red, 5, green, 10, yellow, 15, blue, 20, black, 25, white, 30 21 | DATA orange, 35, pink, 40, cyan, 45, purple, 50 22 | : 23 | : 24 | DEF PROCadd(name$, data%) 25 | LOCAL node% 26 | node% = FNalloc(nodesize%) 27 | $(node%+name%) = name$ 28 | node%!value% = data% 29 | node%!left% = 0 30 | node%!right% = 0 31 | IF root%=0 THEN root% = node%: ENDPROC 32 | P% = root% 33 | REPEAT 34 | IF name$<$(P%+name%) THEN 35 | IF P%!left%<>0 THEN P% = P%!left% ELSE P%!left% = node%: ENDPROC 36 | ELSE 37 | IF P%!right%<>0 THEN P% = P%!right% ELSE P%!right% = node%: ENDPROC 38 | ENDIF 39 | UNTIL FALSE 40 | ENDPROC 41 | : 42 | : 43 | DEF PROCshow(P%) 44 | IF P%!left%<>0 THEN PROCshow(P%!left%) 45 | PRINT $(P%+name%);TAB(20);P%!value% 46 | IF P%!right%<>0 THEN PROCshow(P%!right%) 47 | ENDPROC 48 | : 49 | : 50 | DEF FNalloc(size%) 51 | LOCAL P% 52 | P% = heaptop% 53 | heaptop%+=size% 54 | =P% -------------------------------------------------------------------------------- /src/convert.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Matrix Brandy Basic VI Interpreter. 3 | ** Copyright (C) 2000-2014 David Daniels 4 | ** Copyright (C) 2018-2024 Michael McConnell and contributors 5 | ** 6 | ** Brandy is free software; you can redistribute it and/or modify 7 | ** it under the terms of the GNU General Public License as published by 8 | ** the Free Software Foundation; either version 2, or (at your option) 9 | ** any later version. 10 | ** 11 | ** Brandy is distributed in the hope that it will be useful, 12 | ** but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | ** GNU General Public License for more details. 15 | ** 16 | ** You should have received a copy of the GNU General Public License 17 | ** along with Brandy; see the file COPYING. If not, write to 18 | ** the Free Software Foundation, 59 Temple Place - Suite 330, 19 | ** Boston, MA 02111-1307, USA. 20 | ** 21 | ** 22 | ** This file defines functions that convert numbers between 23 | ** character and binary format 24 | */ 25 | 26 | #ifndef __conversions_h 27 | #define __conversions_h 28 | 29 | #include "common.h" 30 | 31 | int todigit(char); 32 | char *tonumber(char *, boolean *, int32 *, int64 *, float64 *); 33 | char *todecimal(char *, boolean *, int32 *, int64 *, float64 *); 34 | 35 | #endif 36 | -------------------------------------------------------------------------------- /docs/RISC-OS.txt: -------------------------------------------------------------------------------- 1 | Matrix Brandy on RISC OS 2 | ======================== 3 | 4 | The following documents are not included in the RISC OS distribution, due to 5 | the differences in the implementation: 6 | 7 | compiling.txt: Excluded because the process will vary depending on which 8 | compiler is used, and whether cross-compiling. 9 | 10 | graphics.txt: Matrix Brandy offers no internal graphics support on RISC 11 | OS, instead the VDU codes are passed through to the 12 | underlying OS. *REFRESH and other commands that interact 13 | with the SDL layer, thus, are recognised but do nothing. 14 | User-defined screen modes via *NewMode are not available. 15 | 16 | Mode7.txt: As with graphics, MODE 7 support is implemented by RISC OS, 17 | rather than in Matrix Brandy. Thus the OSWORDs to read and 18 | write the teletext font are not available, nor are the 19 | facilities to change the SAA505x code page or black as a 20 | colour on older RISC OS versions. 21 | 22 | osbyte.txt: OSBYTE is passed through to RISC OS to handle, no emulation 23 | is offered by Matrix Brandy. 24 | 25 | All display output is passed to the operating system "raw", as the internal 26 | versions of ARM BBC BASIC would, and are handled by RISC OS. 27 | -------------------------------------------------------------------------------- /src/assign.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Matrix Brandy Basic VI Interpreter. 3 | ** Copyright (C) 2000-2014 David Daniels 4 | ** Copyright (C) 2018-2024 Michael McConnell and contributors 5 | ** 6 | ** Brandy is free software; you can redistribute it and/or modify 7 | ** it under the terms of the GNU General Public License as published by 8 | ** the Free Software Foundation; either version 2, or (at your option) 9 | ** any later version. 10 | ** 11 | ** Brandy is distributed in the hope that it will be useful, 12 | ** but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | ** GNU General Public License for more details. 15 | ** 16 | ** You should have received a copy of the GNU General Public License 17 | ** along with Brandy; see the file COPYING. If not, write to 18 | ** the Free Software Foundation, 59 Temple Place - Suite 330, 19 | ** Boston, MA 02111-1307, USA. 20 | ** 21 | ** 22 | ** This file defines functions that handle assignments 23 | ** in assign.c 24 | */ 25 | 26 | #ifndef __assign_h 27 | #define __assign_h 28 | 29 | extern void exec_assignment(void); 30 | extern void assign_staticvar(void); 31 | extern void assign_intvar(void); 32 | extern void assign_uint8var(void); 33 | extern void assign_int64var(void); 34 | extern void assign_floatvar(void); 35 | extern void assign_stringvar(void); 36 | extern void assign_pseudovar(void); 37 | 38 | #endif 39 | -------------------------------------------------------------------------------- /docs/identification.txt: -------------------------------------------------------------------------------- 1 | BASIC VERSION IDENTIFICATION 2 | ============================ 3 | 4 | As of version 1.22.12, all builds of Matrix Brandy BASIC VI give an 5 | INKEY(-256) value of &4D (or ASC("M"), decimal 77). 6 | 7 | Therefore. this is a guarantted way for a BASIC program to identify that it 8 | is running on Matrix Brandy (as opposed to Acorn BBC BASIC on RISC OS, 9 | BBCSDL on many other platforms) and can make assumptions based on this, 10 | including access to SYS "Brandy_*" system calls. On RISC OS, these are 11 | trapped and handled internally, all other SYS calls are handed to the 12 | operating system, on other platforms all SYS calls are handled internally 13 | and only a very small subset of RISC OS calls are recognised and handled. 14 | 15 | To further indentify what platform the program is running on, use the call 16 | SYS "Brandy_Platform" TO osname$, cpu$, is64bit%, sdl%, mactype%, 17 | underlying%, pid%, ppid% 18 | 19 | The "underlying%" value is the value of INKEY(-256) that used to be returned 20 | prior to Matrix Brandy using its own value, for example &F9 on Linux, or a 21 | value (ANDed with &F0) of &A0 on RISC OS. Therefore, you can assume graphics 22 | availability if underlying% AND &F0 = &A0 or sdl% = 1. 23 | 24 | (The 'tbrandy' build can also offer limited graphics via a Tektronix display 25 | or emulator, this needs to be specifically enabled at runtime, Brandy has no 26 | way to detect if it's running with a suitable terminal.) 27 | -------------------------------------------------------------------------------- /examples/gpiolib: -------------------------------------------------------------------------------- 1 | REM GPIO library for the Raspberry Pi 2, RPi 3 or RPi Zero 2 | REM Michael McConnell for Matrix Brandy http://brandy.matrixnetwork.co.uk/ 3 | REM Interface compatible with Richard Russell's gpiolib.bbc from BBCSDL 4 | : 5 | REM Setup GPIO, call once during initialisation: 6 | DEF FN_gpio_setup 7 | LOCAL present% 8 | SYS "RaspberryPi_GPIOInfo" TO present%,G% 9 | IF present%=0 THEN ERROR 0, "GPIO not present or usable" 10 | =G% 11 | REM Always use PROC_gpio_inp() before using PROC_gpio_out() or PROC_gpio_alt() 12 | DEF PROC_gpio_inp(G%,P%) : SYS "RaspberryPi_SetGPIOPortMode",P%,0 : ENDPROC : REM Set to input 13 | DEF PROC_gpio_out(G%,P%) : SYS "RaspberryPi_SetGPIOPortMode",P%,1 : ENDPROC : REM Set to output 14 | : 15 | REM Alternative pin functions; A% = 4 to 7 (alt 0 to 3), 3 (alt 4) or 2 (alt 5): 16 | DEF PROC_gpio_alt(G%,P%,A%) : SYS "RaspberryPi_SetGPIOPortMode",P%,A% : ENDPROC : REM Set alt function 17 | : 18 | REM Set or clear one or more pins, D% is a bit mask: 19 | DEF PROC_gpio_set(G%,D%) 20 | FOR l%=0 TO 31: IF D% AND (1<size% THEN L%=size%-N% 44 | X%=RND(100000) 45 | FOR I%=1 TO L% 46 | table%(N%)=X% 47 | X%+=RND(100) 48 | N%+=1 49 | NEXT 50 | ENDWHILE 51 | ENDPROC 52 | : 53 | : 54 | DEF PROCcheck 55 | FOR N%=1 TO size%-1 56 | IF table%(N%)>table%(N%+1) THEN PRINT"Out of order at ";N% 57 | NEXT 58 | ENDPROC 59 | :: 60 | DEF PROCcombsort 61 | PRINT"Comb sort "; 62 | T=TIME 63 | gap%=size% 64 | REPEAT 65 | gap%=gap%/1.3: IF gap%<1 THEN gap%=1 66 | switch%=FALSE 67 | FOR I%=1 TO size%-gap% 68 | J%=I%+gap% 69 | IF table%(I%)>table%(J%) THEN SWAP table%(I%),table%(J%): switch%=TRUE 70 | NEXT 71 | UNTIL NOT switch% AND gap%=1 72 | PRINT TIME-T 73 | PROCcheck 74 | ENDPROC 75 | : 76 | : 77 | DEF PROCbubblesort 78 | PRINT"Bubble sort "; 79 | T=TIME 80 | H%=size%-1 81 | REPEAT 82 | M%=0 83 | FOR I%=1 TO H% 84 | IF table%(I%)>table%(I%+1) THEN SWAP table%(I%),table%(I%+1): M%=I% 85 | NEXT 86 | H%=M% 87 | UNTIL M%=0 88 | PRINT TIME-T 89 | PROCcheck 90 | ENDPROC 91 | -------------------------------------------------------------------------------- /other-makefiles/makefile.djgpp: -------------------------------------------------------------------------------- 1 | # Makefile for brandy under DOS (using gcc and DJGPP) 2 | 3 | CC = gcc 4 | LD = gcc 5 | 6 | CFLAGS = -march=i586 -c -g -DDEBUG 7 | CFLAGS2 = -march=i586 -O2 -fomit-frame-pointer 8 | 9 | LDFLAGS = 10 | 11 | LIBS = -lm 12 | 13 | SRCDIR = src 14 | 15 | OBJ = $(SRCDIR)/variables.o $(SRCDIR)/tokens.o $(SRCDIR)/textonly.o \ 16 | $(SRCDIR)/strings.o $(SRCDIR)/statement.o $(SRCDIR)/stack.o \ 17 | $(SRCDIR)/miscprocs.o $(SRCDIR)/mainstate.o $(SRCDIR)/lvalue.o \ 18 | $(SRCDIR)/keyboard.o $(SRCDIR)/iostate.o $(SRCDIR)/heap.o \ 19 | $(SRCDIR)/functions.o $(SRCDIR)/fileio.o $(SRCDIR)/evaluate.o \ 20 | $(SRCDIR)/errors.o $(SRCDIR)/emulate.o $(SRCDIR)/editor.o \ 21 | $(SRCDIR)/convert.o $(SRCDIR)/commands.o $(SRCDIR)/brandy.o \ 22 | $(SRCDIR)/assign.o 23 | 24 | SRC = $(SRCDIR)/variables.c $(SRCDIR)/tokens.c $(SRCDIR)/textonly.c \ 25 | $(SRCDIR)/strings.c $(SRCDIR)/statement.c $(SRCDIR)/stack.c \ 26 | $(SRCDIR)/miscprocs.c $(SRCDIR)/mainstate.c $(SRCDIR)/lvalue.c \ 27 | $(SRCDIR)/keyboard.c $(SRCDIR)/iostate.c $(SRCDIR)/heap.c \ 28 | $(SRCDIR)/functions.c $(SRCDIR)/fileio.c $(SRCDIR)/evaluate.c \ 29 | $(SRCDIR)/errors.c $(SRCDIR)/emulate.c $(SRCDIR)/editor.c \ 30 | $(SRCDIR)/convert.c $(SRCDIR)/commands.c $(SRCDIR)/brandy.c \ 31 | $(SRCDIR)/assign.c 32 | 33 | brandy: $(OBJ) 34 | $(LD) $(LDFLAGS) -o brandy $(OBJ) $(LIBS) 35 | 36 | include build/depends.mk 37 | 38 | .c.o: 39 | $(CC) $(CFLAGS) $< -o $@ 40 | 41 | recompile: 42 | $(CC) $(CFLAGS) $(SRC) $(LIBS) -o brandy 43 | 44 | nodebug: 45 | $(CC) $(CFLAGS2) $(SRC) $(LIBS) -o brandy 46 | strip brandy 47 | 48 | check: 49 | $(CC) $(CFLAGS) -Wall $(SRC) $(LIBS) -o brandy 50 | 51 | clean: 52 | rm $(SRCDIR)/*.o brandy 53 | 54 | all: brandy 55 | -------------------------------------------------------------------------------- /src/strings.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Matrix Brandy Basic VI Interpreter. 3 | ** Copyright (C) 2000-2014 David Daniels 4 | ** Copyright (C) 2018-2024 Michael McConnell and contributors 5 | ** 6 | ** Brandy is free software; you can redistribute it and/or modify 7 | ** it under the terms of the GNU General Public License as published by 8 | ** the Free Software Foundation; either version 2, or (at your option) 9 | ** any later version. 10 | ** 11 | ** Brandy is distributed in the hope that it will be useful, 12 | ** but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | ** GNU General Public License for more details. 15 | ** 16 | ** You should have received a copy of the GNU General Public License 17 | ** along with Brandy; see the file COPYING. If not, write to 18 | ** the Free Software Foundation, 59 Temple Place - Suite 330, 19 | ** Boston, MA 02111-1307, USA. 20 | ** 21 | ** 22 | ** This file defines the functions and so forth associated with 23 | ** memory manangement for strings 24 | */ 25 | 26 | #ifndef __strings_h 27 | #define __strings_h 28 | 29 | #include "common.h" 30 | #include "basicdefs.h" 31 | 32 | #define SHORT_STRING 256 33 | 34 | extern void *alloc_string(int32); 35 | extern void free_string(basicstring); 36 | extern void discard_strings(byte *, int32); 37 | extern char *resize_string(char *, int32, int32); 38 | extern void clear_strings(void); 39 | extern int32 get_stringlen(size_t); 40 | extern void show_stringstats(void); 41 | extern void check_alloc(void); 42 | 43 | /* Additional string functions needed for RISC OS CLib build */ 44 | #ifdef TARGET_RISCOS 45 | size_t strnlen(const char *, size_t); 46 | #endif /* TARGET_RISCOS */ 47 | 48 | #endif /* __strings_h */ 49 | 50 | -------------------------------------------------------------------------------- /other-makefiles/makefile.mingw: -------------------------------------------------------------------------------- 1 | # Makefile for brandy under DOS (using gcc and MINGW) 2 | 3 | CC = gcc 4 | LD = gcc 5 | 6 | CFLAGS = -march=i586 -c -g -DDEBUG 7 | CFLAGS2 = -march=i586 -O2 -fomit-frame-pointer 8 | 9 | LDFLAGS = 10 | 11 | LIBS = -lm 12 | 13 | SRCDIR = src 14 | 15 | OBJ = $(SRCDIR)/variables.o $(SRCDIR)/tokens.o $(SRCDIR)/textonly.o \ 16 | $(SRCDIR)/strings.o $(SRCDIR)/statement.o $(SRCDIR)/stack.o \ 17 | $(SRCDIR)/miscprocs.o $(SRCDIR)/mainstate.o $(SRCDIR)/lvalue.o \ 18 | $(SRCDIR)/keyboard.o $(SRCDIR)/iostate.o $(SRCDIR)/heap.o \ 19 | $(SRCDIR)/functions.o $(SRCDIR)/fileio.o $(SRCDIR)/evaluate.o \ 20 | $(SRCDIR)/errors.o $(SRCDIR)/emulate.o $(SRCDIR)/editor.o \ 21 | $(SRCDIR)/convert.o $(SRCDIR)/commands.o $(SRCDIR)/brandy.o \ 22 | $(SRCDIR)/assign.o 23 | 24 | SRC = $(SRCDIR)/variables.c $(SRCDIR)/tokens.c $(SRCDIR)/textonly.c \ 25 | $(SRCDIR)/strings.c $(SRCDIR)/statement.c $(SRCDIR)/stack.c \ 26 | $(SRCDIR)/miscprocs.c $(SRCDIR)/mainstate.c $(SRCDIR)/lvalue.c \ 27 | $(SRCDIR)/keyboard.c $(SRCDIR)/iostate.c $(SRCDIR)/heap.c \ 28 | $(SRCDIR)/functions.c $(SRCDIR)/fileio.c $(SRCDIR)/evaluate.c \ 29 | $(SRCDIR)/errors.c $(SRCDIR)/emulate.c $(SRCDIR)/editor.c \ 30 | $(SRCDIR)/convert.c $(SRCDIR)/commands.c $(SRCDIR)/brandy.c \ 31 | $(SRCDIR)/assign.c 32 | 33 | brandy: $(OBJ) 34 | $(LD) $(LDFLAGS) -o brandy $(OBJ) $(LIBS) 35 | 36 | include build/depends.mk 37 | 38 | .c.o: 39 | $(CC) $(CFLAGS) $< -o $@ 40 | 41 | recompile: 42 | $(CC) $(CFLAGS) $(SRC) $(LIBS) -o brandy 43 | 44 | nodebug: 45 | $(CC) $(CFLAGS2) $(SRC) $(LIBS) -o brandy 46 | strip brandy.exe 47 | 48 | check: 49 | $(CC) $(CFLAGS) -Wall $(SRC) $(LIBS) -o brandy 50 | 51 | clean: 52 | del /q $(SRCDIR)\*.o 53 | del /q brandy.exe 54 | 55 | all: brandy 56 | -------------------------------------------------------------------------------- /src/heap.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Matrix Brandy Basic VI Interpreter. 3 | ** Copyright (C) 2000-2014 David Daniels 4 | ** Copyright (C) 2018-2024 Michael McConnell and contributors 5 | ** 6 | ** Brandy is free software; you can redistribute it and/or modify 7 | ** it under the terms of the GNU General Public License as published by 8 | ** the Free Software Foundation; either version 2, or (at your option) 9 | ** any later version. 10 | ** 11 | ** Brandy is distributed in the hope that it will be useful, 12 | ** but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | ** GNU General Public License for more details. 15 | ** 16 | ** You should have received a copy of the GNU General Public License 17 | ** along with Brandy; see the file COPYING. If not, write to 18 | ** the Free Software Foundation, 59 Temple Place - Suite 330, 19 | ** Boston, MA 02111-1307, USA. 20 | ** 21 | ** 22 | ** This file defines the functions and so forth associated with memory 23 | ** manangement 24 | */ 25 | 26 | #ifndef __heap_h 27 | #define __heap_h 28 | 29 | #include "common.h" 30 | 31 | #define STACKBUFFER 256 /* Minimum space allowed between Basic's stack and variables */ 32 | 33 | extern boolean init_heap(void); 34 | extern void release_heap(void); 35 | extern boolean init_workspace(size_t); 36 | extern void release_workspace(void); 37 | extern void *allocmem(size_t, boolean); 38 | extern void freemem(void *, int32); 39 | extern void clear_heap(void); 40 | 41 | /* 42 | ** 'returnable' is called to check if the block at 'where' is the 43 | ** last item allocated on the heap and can therefore be returned 44 | ** to it. 45 | */ 46 | #define returnable(x,y) (CAST(x, byte *)+ALIGN(y)==basicvars.vartop) 47 | 48 | #endif 49 | -------------------------------------------------------------------------------- /src/statement.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Matrix Brandy Basic VI Interpreter. 3 | ** Copyright (C) 2000-2014 David Daniels 4 | ** Copyright (C) 2018-2024 Michael McConnell and contributors 5 | ** 6 | ** Brandy is free software; you can redistribute it and/or modify 7 | ** it under the terms of the GNU General Public License as published by 8 | ** the Free Software Foundation; either version 2, or (at your option) 9 | ** any later version. 10 | ** 11 | ** Brandy is distributed in the hope that it will be useful, 12 | ** but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | ** GNU General Public License for more details. 15 | ** 16 | ** You should have received a copy of the GNU General Public License 17 | ** along with Brandy; see the file COPYING. If not, write to 18 | ** the Free Software Foundation, 59 Temple Place - Suite 330, 19 | ** Boston, MA 02111-1307, USA. 20 | ** 21 | ** 22 | ** Functions in the main interpreter module 23 | */ 24 | 25 | #ifndef __statement_h 26 | #define __statement_h 27 | 28 | #include "common.h" 29 | #include "basicdefs.h" 30 | 31 | #define STRINGOK FALSE 32 | #define NOSTRING TRUE 33 | 34 | extern byte ateol[]; 35 | 36 | extern void init_interpreter(void); 37 | extern void exec_thisline(void); 38 | extern void exec_fnstatements(byte *); 39 | extern void run_program(byte *); 40 | extern void trace_line(int32); 41 | extern void trace_proc(char *, boolean); 42 | extern void trace_branch(byte *, byte *); 43 | extern boolean isateol(byte *); 44 | extern void check_ateol(void); 45 | extern void bad_token(void); 46 | extern void bad_syntax(void); 47 | extern void next_line(void); 48 | extern void store_value(lvalue, int64, boolean); 49 | extern void end_run(void); 50 | 51 | #endif 52 | 53 | -------------------------------------------------------------------------------- /src/editor.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Matrix Brandy Basic VI Interpreter. 3 | ** Copyright (C) 2000-2014 David Daniels 4 | ** Copyright (C) 2018-2024 Michael McConnell and contributors 5 | ** 6 | ** Brandy is free software; you can redistribute it and/or modify 7 | ** it under the terms of the GNU General Public License as published by 8 | ** the Free Software Foundation; either version 2, or (at your option) 9 | ** any later version. 10 | ** 11 | ** Brandy is distributed in the hope that it will be useful, 12 | ** but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | ** GNU General Public License for more details. 15 | ** 16 | ** You should have received a copy of the GNU General Public License 17 | ** along with Brandy; see the file COPYING. If not, write to 18 | ** the Free Software Foundation, 59 Temple Place - Suite 330, 19 | ** Boston, MA 02111-1307, USA. 20 | ** 21 | ** 22 | ** This file defines functions associated with the editing of Basic 23 | ** programs as well as loading them from and saving them to disk 24 | */ 25 | 26 | #ifndef __editor_h 27 | #define __editor_h 28 | 29 | #include "common.h" 30 | 31 | #define LOAD_LIBRARY TRUE 32 | #define INSTALL_LIBRARY FALSE 33 | 34 | extern void mark_end(byte *); 35 | extern void edit_line(void); 36 | extern void delete_range(int32, int32); 37 | extern void clear_program(void); 38 | extern void clear_tables(void); 39 | extern void read_basic(char *); 40 | #ifdef BRANDYAPP 41 | extern void read_basic_block(void); 42 | #endif 43 | extern void write_basic(char *); 44 | extern void read_library(char *, boolean); 45 | extern void write_text(char *, FILE *); 46 | extern boolean validate_program(void); 47 | extern void renumber_program(byte *, int32, int32); 48 | extern char *multifgets(char *mfbuf, int bufsz, FILE *handle); 49 | 50 | #endif 51 | -------------------------------------------------------------------------------- /src/functions.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Matrix Brandy Basic VI Interpreter. 3 | ** Copyright (C) 2000-2014 David Daniels 4 | ** Copyright (C) 2018-2024 Michael McConnell and contributors 5 | ** 6 | ** Brandy is free software; you can redistribute it and/or modify 7 | ** it under the terms of the GNU General Public License as published by 8 | ** the Free Software Foundation; either version 2, or (at your option) 9 | ** any later version. 10 | ** 11 | ** Brandy is distributed in the hope that it will be useful, 12 | ** but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | ** GNU General Public License for more details. 15 | ** 16 | ** You should have received a copy of the GNU General Public License 17 | ** along with Brandy; see the file COPYING. If not, write to 18 | ** the Free Software Foundation, 59 Temple Place - Suite 330, 19 | ** Boston, MA 02111-1307, USA. 20 | ** 21 | ** 22 | ** This file contains definitions for functions that deal 23 | ** with the built-in Basic functions 24 | */ 25 | 26 | #ifndef __functions_h 27 | #define __functions_h 28 | 29 | extern void exec_function(void); 30 | extern void init_functions(void); 31 | 32 | /* 33 | ** The following functions are invoked from the factor function 34 | ** table as they have one byte tokens. Most of them are tokens 35 | ** that can be used as statements as well as functions, for 36 | ** example, MODE 37 | */ 38 | extern void fn_width(void); 39 | extern void fn_vdu(void); 40 | extern void fn_true(void); 41 | extern void fn_trace(void); 42 | extern void fn_top(void); 43 | extern void fn_tint(void); 44 | extern void fn_quit(void); 45 | extern void fn_not(void); 46 | extern void fn_mode(void); 47 | extern void fn_mod(void); 48 | extern void fn_false(void); 49 | extern void fn_end(void); 50 | extern void fn_dim(void); 51 | extern void fn_colour(void); 52 | extern void fn_beats(void); 53 | 54 | #endif 55 | -------------------------------------------------------------------------------- /examples/Mode7/m7point: -------------------------------------------------------------------------------- 1 | REM Library for pixel plotting in MODE 7 2 | 3 | REM Using a virtual coordinate system that has 0,0 at the bottom left. 4 | REM 0,0 corresponds to the bottom line, second character cell 5 | REM (as it's impossible to put graphics in the left-most cell) 6 | REM X range is 0 to 77. Y range is 0 to 74 (3 vertical per sixel) 7 | 8 | DEFFNsxbit(sx%, sy%) 9 | IF sx% = 0 AND sy% = 0 THEN =16 10 | IF sx% = 0 AND sy% = 1 THEN =4 11 | IF sx% = 0 AND sy% = 2 THEN =1 12 | IF sx% = 1 AND sy% = 0 THEN =64 13 | IF sx% = 1 AND sy% = 1 THEN =8 14 | IF sx% = 1 AND sy% = 2 THEN =2 15 | =0 : REM 16 | 17 | REM Read the point at the specified coordinates (1=set, 0=cleared) 18 | REM This can be optimised to one line, but it's left expanded 19 | REM for clarity to show how it works. 20 | 21 | DEFFNpoint(x%,y%) 22 | LOCAL cx%,cy%,chr%,sx%,sy% 23 | REM Get character cell 24 | cx% = 1+(x% DIV 2) 25 | cy% = 24-(y% DIV 3) 26 | chr%=GET(cx%,cy%) AND &5F 27 | sx% = x% MOD 2 28 | sy% = y% MOD 3 29 | =SGN(chr% AND FNsxbit(sx%,sy%)) 30 | 31 | REM Plot a Teletext sixel point. The first parameter means: 32 | REM 0: Clear the point 33 | REM 1: Set the point 34 | REM 2: Toggle the point 35 | DEFPROCpoint(cmd%, x%, y%) 36 | LOCAL cx%,cy%,chr%,sx%,sy%,tx%,ty% 37 | REM Get character cell 38 | cx% = 1+(x% DIV 2) 39 | cy% = 24-(y% DIV 3) 40 | chr%=GET(cx%,cy%) AND &5F 41 | sx% = x% MOD 2 42 | sy% = y% MOD 3 43 | CASE cmd% OF 44 | WHEN 0:chr% AND=(&5F - FNsxbit(sx%,sy%)) 45 | WHEN 1:chr% OR=FNsxbit(sx%,sy%) 46 | WHEN 2:chr% EOR=FNsxbit(sx%,sy%) 47 | ENDCASE 48 | tx%=POS: ty%=VPOS 49 | PRINT TAB(cx%,cy%)CHR$(chr% OR 160);TAB(tx%,ty%); 50 | ENDPROC 51 | 52 | REM Converts screen coordinates (like those returned by MOUSE) to 53 | REM MODE 7 sixel coordinates used by these other functions 54 | 55 | DEFFNscreen2m7(x%,y%) 56 | x%=(x%/16)-2 57 | y%=(y%/13.3333) 58 | IF x%<0THENx%=0 59 | =x%+(y%*256) 60 | 61 | DEF FNscreen2chr(x%,y%) 62 | x%=x%/32 63 | y%=25-(y%/40) 64 | =x%+(y%*256) 65 | -------------------------------------------------------------------------------- /src/fileio.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Matrix Brandy Basic VI Interpreter. 3 | ** Copyright (C) 2000-2014 David Daniels 4 | ** Copyright (C) 2018-2024 Michael McConnell and contributors 5 | ** 6 | ** Brandy is free software; you can redistribute it and/or modify 7 | ** it under the terms of the GNU General Public License as published by 8 | ** the Free Software Foundation; either version 2, or (at your option) 9 | ** any later version. 10 | ** 11 | ** Brandy is distributed in the hope that it will be useful, 12 | ** but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | ** GNU General Public License for more details. 15 | ** 16 | ** You should have received a copy of the GNU General Public License 17 | ** along with Brandy; see the file COPYING. If not, write to 18 | ** the Free Software Foundation, 59 Temple Place - Suite 330, 19 | ** Boston, MA 02111-1307, USA. 20 | ** 21 | ** 22 | ** This file declares the file I/O routines for the interpreter 23 | */ 24 | 25 | #ifndef __fileio_h 26 | #define __fileio_h 27 | 28 | extern boolean isapath(char *); 29 | 30 | extern void init_fileio(void); 31 | extern int32 fileio_openin(char *, int32); 32 | extern int32 fileio_openout(char *, int32); 33 | extern int32 fileio_openup(char *, int32); 34 | extern void fileio_close(int32); 35 | extern int32 fileio_bget(int32); 36 | extern int32 fileio_getdol(int32, char *); 37 | extern void fileio_getnumber(int32, boolean *, int64 *, float64 *); 38 | extern int32 fileio_getstring(int32, char *); 39 | extern void fileio_bput(int32, int32); 40 | extern void fileio_bputstr(int32, char *, int32); 41 | extern void fileio_printint(int32, int32); 42 | extern void fileio_printuint8(int32, uint8); 43 | extern void fileio_printint64(int32, int64); 44 | extern void fileio_printfloat(int32, float64); 45 | extern void fileio_printstring(int32, char *, int32); 46 | extern int32 fileio_eof(int32); 47 | extern int64 fileio_getptr(int32); 48 | extern void fileio_setptr(int32, int64); 49 | extern int64 fileio_getext(int32); 50 | extern void fileio_setext(int32, int64); 51 | extern void fileio_shutdown(void); 52 | 53 | #endif 54 | -------------------------------------------------------------------------------- /makefile.app: -------------------------------------------------------------------------------- 1 | # Makefile for brandy under NetBSD and Linux 2 | 3 | # Use the following to generate your app.c: 4 | # examples/bin2c /path/to/basicprog src/app.c 5 | 6 | # Then, build brandyapp with this makefile. 7 | 8 | CC = gcc 9 | LD = gcc 10 | AR = ar 11 | ADDFLAGS = ${BRANDY_BUILD_FLAGS} 12 | 13 | include build/git.mk 14 | 15 | #CFLAGS = -g -DDEBUG $(shell sdl-config --cflags) -DUSE_SDL -DDEFAULT_IGNORE -DBRANDYAPP -Wall $(GITFLAGS) $(ADDFLAGS) 16 | #CFLAGS = -g $(shell sdl-config --cflags) -DUSE_SDL -DDEFAULT_IGNORE -DBRANDYAPP -Wall $(GITFLAGS) $(ADDFLAGS) 17 | CFLAGS = -O3 $(shell sdl-config --cflags) -DUSE_SDL -DDEFAULT_IGNORE -DBRANDYAPP -Wall $(GITFLAGS) $(ADDFLAGS) 18 | 19 | LDFLAGS += 20 | 21 | LIBS = -lm $(shell sdl-config --libs) -ldl -pthread -lrt -lX11 22 | 23 | SRCDIR = src 24 | 25 | OBJ = $(SRCDIR)/variables.o $(SRCDIR)/tokens.o $(SRCDIR)/graphsdl.o \ 26 | $(SRCDIR)/strings.o $(SRCDIR)/statement.o $(SRCDIR)/stack.o \ 27 | $(SRCDIR)/miscprocs.o $(SRCDIR)/mainstate.o $(SRCDIR)/lvalue.o \ 28 | $(SRCDIR)/keyboard.o $(SRCDIR)/iostate.o $(SRCDIR)/heap.o \ 29 | $(SRCDIR)/functions.o $(SRCDIR)/fileio.o $(SRCDIR)/evaluate.o \ 30 | $(SRCDIR)/errors.o $(SRCDIR)/mos.o $(SRCDIR)/editor.o \ 31 | $(SRCDIR)/convert.o $(SRCDIR)/commands.o $(SRCDIR)/brandy.o \ 32 | $(SRCDIR)/assign.o $(SRCDIR)/net.o $(SRCDIR)/mos_sys.o \ 33 | $(SRCDIR)/soundsdl.o $(SRCDIR)/app.o 34 | 35 | SRC = $(SRCDIR)/variables.c $(SRCDIR)/tokens.c $(SRCDIR)/graphsdl.c \ 36 | $(SRCDIR)/strings.c $(SRCDIR)/statement.c $(SRCDIR)/stack.c \ 37 | $(SRCDIR)/miscprocs.c $(SRCDIR)/mainstate.c $(SRCDIR)/lvalue.c \ 38 | $(SRCDIR)/keyboard.c $(SRCDIR)/iostate.c $(SRCDIR)/heap.c \ 39 | $(SRCDIR)/functions.c $(SRCDIR)/fileio.c $(SRCDIR)/evaluate.c \ 40 | $(SRCDIR)/errors.c $(SRCDIR)/mos.c $(SRCDIR)/editor.c \ 41 | $(SRCDIR)/convert.c $(SRCDIR)/commands.c $(SRCDIR)/brandy.c \ 42 | $(SRCDIR)/assign.c $(SRCDIR)/net.c $(SRCDIR)/mos_sys.c \ 43 | $(SRCDIR)/soundsdl.c $(SRCDIR)/app.c 44 | 45 | brandyapp: $(OBJ) 46 | $(LD) $(LDFLAGS) -o brandyapp $(OBJ) $(LIBS) 47 | 48 | include build/depends.mk 49 | 50 | .c.o: 51 | $(CC) $(CFLAGS) $< -c -o $@ 52 | 53 | clean: 54 | rm -f $(SRCDIR)/*.o brandyapp 55 | 56 | all: brandyapp 57 | -------------------------------------------------------------------------------- /examples/lands: -------------------------------------------------------------------------------- 1 | REM This program draws a simple fractal landscape and plots it 2 | REM using characters to represent different heights. The landscape 3 | REM can be changed by entering different values for seed% 4 | : 5 | S%=256 6 | limit%=2 :REM 64 by 64 plot 7 | xlimit%=64 8 | zlimit%=24 9 | DIM Y%(S%,S%),filler$(16) 10 | filler$()=".", "_", "+", "%", "o", "$", "=", "U", "E", "B", "F", "O", "Q", "N", "M", "#", "@" 11 | : 12 | INPUT"Seed? " seed% 13 | CLS 14 | start=TIME 15 | T%=1024 DIV S%*limit%*2 16 | K%=1024 DIV S% 17 | step%=limit%*2 18 | S2%=S% DIV 2 19 | Y%(0,0)=FNrandom(S%)-S2%-20 20 | Y%(0,S%)=FNrandom(S%)-S2%-20 21 | Y%(S%,0)=FNrandom(S%)-S2%-20 22 | Y%(S%,S%)=FNrandom(S%)-S2%-20 23 | PROClandscape(0,0,S%) 24 | COLOUR 7 25 | PRINT'"Time=";TIME-start 26 | END 27 | : 28 | : 29 | DEF PROClandscape(X%,Z%,D%) 30 | LOCAL A%,XA%,ZA% 31 | A%=D%>>1 32 | A2%=A%>>1 33 | XA%=X%+A%: ZA%=Z%+A% 34 | XD%=X%+D%: ZD%=Z%+D% 35 | IF Y%(XA%,Z%)=0 THEN Y%(XA%,Z%)=(Y%(X%,Z%)+Y%(XD%,Z%)>>1)+FNrandom(A%)-A2% 36 | PROCcol2d(Y%(XA%,Z%)) 37 | IF Y%(X%,ZA%)=0 THEN Y%(X%,ZA%)=(Y%(X%,Z%)+Y%(X%,ZD%)>>1)+FNrandom(A%)-A2% 38 | PROCcol2d(Y%(X%,ZA%)) 39 | IF Y%(XA%,ZD%)=0 THEN Y%(XA%,ZD%)=(Y%(X%,ZD%)+Y%(XD%,ZD%)>>1)+FNrandom(A%)-A2% 40 | PROCcol2d(Y%(XA%,ZD%)) 41 | IF Y%(XD%,ZA%)=0 THEN Y%(XD%,ZA%)=(Y%(XD%,Z%)+Y%(XD%,ZD%)>>1)+FNrandom(A%)-A2% 42 | PROCcol2d(Y%(XD%,ZA%)) 43 | Y%(XA%,ZA%)=(Y%(X%,ZA%)+Y%(XD%,ZA%)+Y%(XA%,Z%)+Y%(XA%,ZD%)>>2)+FNrandom(A%)-A2% 44 | PROCcol2d(Y%(XA%,ZA%)) 45 | IF A%>limit% THEN 46 | PROClandscape(X%,Z%,A%) 47 | PROClandscape(XA%,Z%,A%) 48 | PROClandscape(X%,ZA%,A%) 49 | PROClandscape(XA%,ZA%,A%) 50 | ENDIF 51 | ENDPROC 52 | : 53 | : 54 | DEF PROCcol2d(P%) 55 | LOCAL xx%, zz% 56 | xx%=X% DIV step% 57 | IF xx%>=xlimit% THEN ENDPROC 58 | zz%=Z% DIV step% 59 | IF zz%>=zlimit% THEN ENDPROC 60 | IF P%<=0 THEN 61 | REM Sea 62 | IF P%<-100 THEN COLOUR 4 ELSE COLOUR 6 63 | PRINT TAB(xx%, zz%);"~"; 64 | ELSE 65 | REM Land 66 | colour%=P% DIV 18 67 | IF colour%=0 THEN COLOUR 3 ELSE COLOUR 2 68 | PRINT TAB(xx%, zz%);filler$(colour%); 69 | ENDIF 70 | ENDPROC 71 | : 72 | : 73 | DEF FNrandom(range%) 74 | seed%=48271*(seed% MOD 44488)-3399*(seed% DIV 44488) 75 | IF seed%<0 THEN seed%+=&80000000 76 | =seed% MOD range%+1 77 | -------------------------------------------------------------------------------- /tests/notes: -------------------------------------------------------------------------------- 1 | KBDTest 2 | 1,2: Platform-specific 8-bit keycodes 3 | 3,4: Platform-specific 9-bit keycodes 4 | Should return the host platform's regular low-level keycodes. Should return: 5 | RISC OS: 6 | &80+n: Print, F1, F2, F3, F4, F5, F6, F7, F8, F9, Break, End, Left, Right, Down, Up 7 | &90+n: , PgDn, PgUp 8 | &C0+n F10, F11, F12, Ins 9 | Shift, Ctrl, Alt should toggle &10, &20, &30, 9-bit keycodes should add &100 10 | Home=&01E, Del=&07F 11 | Non-RISC OS: 12 | &80+n: Print, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, F11, F12, F13, F14, F15 13 | &C0+n: Ins, Del, Home, End, PgDn, PgUp, Left, Right, Down, Up 14 | Shift, Ctrl, Alt should toggle &10, &20, &30, 9-bit keycodes should add &100 15 | BBC BASIC for Windows: 16 | Is a specific exception, tbd 17 | 18 | 6,7: RISCOS-mapped 8-bit keycodes 19 | 8: RISCOS-mapped 9-bit keycodes 20 | Should display RISC OS mapped keycodes. Soft keys should be expanded. Should return: 21 | &80+n: Print, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, F11, F12, F13, F14, F15 22 | &C0+n: Ins, Del, Home, End, PgDn, PgUp, Left, Right, Down, Up 23 | Shift, Ctrl, Alt should toggle &10, &20, &30, 9-bit keycodes should add &100 24 | Home=&01E, Del=&07F 25 | 26 | KeyScan 27 | Displays BBC negative INKEY scan codes with a text-only display 28 | Works on: RISC OS, WinSDL, MinGW, DJGPP, CentOS 29 | 30 | KeyDOS 31 | Displays DOS negative INKEY scan codes values with a text-only display 32 | Works on: WinSDL, MinGW, DJGPP, CentOS 33 | 34 | KeySDL 35 | Displays SDL 1.2 negative INKEY scan codes values with a text-only display 36 | Works on: RISC OS, WinSDL, MinGW, DJGPP, CentOS 37 | 38 | KeyTest 39 | Displays negative INKEY values with a graphics display 40 | RISC OS, WinSDL, CentOS: works 41 | MinGW, DJGPP: does not work due to graphics needed 42 | 43 | DefChar 44 | SDL Brandy: works 45 | DJP Brandy: does not work due to graphics to draw character box 46 | MGW Brandy: does not work due to graphics to draw character box 47 | 48 | ClockSp 49 | Fails on DJGPP, issues with TIME 50 | -------------------------------------------------------------------------------- /src/iostate.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Matrix Brandy Basic VI Interpreter. 3 | ** Copyright (C) 2000-2014 David Daniels 4 | ** Copyright (C) 2018-2024 Michael McConnell and contributors 5 | ** 6 | ** Brandy is free software; you can redistribute it and/or modify 7 | ** it under the terms of the GNU General Public License as published by 8 | ** the Free Software Foundation; either version 2, or (at your option) 9 | ** any later version. 10 | ** 11 | ** Brandy is distributed in the hope that it will be useful, 12 | ** but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | ** GNU General Public License for more details. 15 | ** 16 | ** You should have received a copy of the GNU General Public License 17 | ** along with Brandy; see the file COPYING. If not, write to 18 | ** the Free Software Foundation, 59 Temple Place - Suite 330, 19 | ** Boston, MA 02111-1307, USA. 20 | ** 21 | ** 22 | ** This file defines the functions handling Basic I/O, sound 23 | ** and graphics statements 24 | */ 25 | 26 | #ifndef __iostate_h 27 | #define __iostate_h 28 | 29 | extern void exec_beats(void); 30 | extern void exec_bput(void); 31 | extern void exec_circle(void); 32 | extern void exec_clg(void); 33 | extern void exec_close(void); 34 | extern void exec_cls(void); 35 | extern void exec_colour(void); 36 | extern void exec_draw(void); 37 | extern void exec_ellipse(void); 38 | extern void exec_envelope(void); 39 | extern void exec_fill(void); 40 | extern void exec_fillby(void); 41 | extern void exec_gcol(void); 42 | extern void exec_input(void); 43 | extern void exec_line(void); 44 | extern void exec_mode(void); 45 | extern void exec_mouse(void); 46 | extern void exec_move(void); 47 | extern void exec_off(void); 48 | extern void exec_origin(void); 49 | extern void exec_plot(void); 50 | extern void exec_point(void); 51 | extern void exec_print(void); 52 | extern void exec_rectangle(void); 53 | extern void exec_sound(void); 54 | extern void exec_stereo(void); 55 | extern void exec_tempo(void); 56 | extern void exec_tint(void); 57 | extern void exec_vdu(void); 58 | extern void exec_voice(void); 59 | extern void exec_voices(void); 60 | extern void exec_width(void); 61 | extern void open_printer(void); 62 | extern void close_printer(void); 63 | extern void printout_character(int32); 64 | 65 | #endif 66 | -------------------------------------------------------------------------------- /docs/README: -------------------------------------------------------------------------------- 1 | The documentation for Brandy consists of the following files: 2 | 3 | basic This is a brief introduction to Basic VI. 4 | 5 | ChangeLog A more detailed list of changes and bug fixes 6 | beginning with V1.21.0. 7 | 8 | compiling Instructions for compiling the program under 9 | various operating systems. 10 | 11 | Config This contains details on the configuration file that sets 12 | certain defaults when running Matrix Brandy. 13 | 14 | graphics This contains notes on the program's graphics 15 | support. 16 | 17 | history A list of changes and bug fixes in the different 18 | versions of the program. 19 | 20 | internals This gives a high level view of the interpreter's 21 | internals. It is not a line-by-line account of 22 | how it works but shows how the various components 23 | fit together. 24 | 25 | messages This file describes all the error messages that the 26 | interpreter can produce and what they mean. 27 | 28 | Mode7 This contains notes on the program's Mode 7 Teletext 29 | support. 30 | 31 | networking This contains some notes on the implementation of 32 | network connectivity that was added in V1.21.6. 33 | 34 | RISC-OS This contains some notes on how the RISC OS build differs. 35 | 36 | use This describes how to use the interpreter and 37 | lists the differences between it and Acorn's 38 | interpreter and its limitations. 39 | 40 | Brandy implements Basic VI, the the 64-bit floating-point mathematics 41 | variant of the dialect of Basic that Acorn Computers supplied with their 42 | ranges of desktop computers that use the ARM processor such as the 43 | Archimedes and RiscPC. Basic V and VI are an extended version of BBC BASIC. 44 | This was the BASIC version used on the BBC Micro that Acorn made during the 45 | early 1980s. 46 | 47 | There is some very useful documentation for the BBC Micro available on the 48 | Internet. One very good site is 'The BBC Lives!' at: 49 | 50 | http://archive.retro-kit.co.uk/bbc.nvg.org/ 51 | 52 | The best manual to look at is the BBC User's Guide. It is useful in that it 53 | gives a lot of background information on BBC BASIC and the environment in 54 | which it runs. It should help in understanding this interpreter better. 55 | -------------------------------------------------------------------------------- /docs/keyboard-codes: -------------------------------------------------------------------------------- 1 | This is an inexhaustive list of keyboard codes returned by GET and INKEY(x) 2 | (where x >= 0). 3 | 4 | Normal keys (and shifted keys) just return their ASCII values. 5 | Key Normal value Shifted value CTRL value Shift-CTRL 6 | PrtSc 128 &80 144 &90 160 &A0 176 &B0 7 | F1 129 &81 145 &91 161 &A1 177 &B1 8 | F2 130 &82 146 &92 162 &A2 178 &B2 9 | F3 131 &83 147 &93 163 &A3 179 &B3 10 | F4 132 &84 148 &94 164 &A4 180 &B4 11 | F5 133 &85 149 &95 165 &A5 181 &B5 12 | F6 134 &86 150 &96 166 &A6 182 &B6 13 | F7 135 &87 151 &97 167 &A7 183 &B7 14 | F8 136 &88 152 &98 168 &A8 184 &B8 15 | F9 137 &89 153 &99 169 &A9 185 &B9 16 | F10 202 &CA 218 &DA 234 &EA 250 &FA 17 | F11 203 &CB 219 &DB 235 &EB 251 &FB 18 | F12 204 &CC 220 &DC 236 &EC 252 &FC 19 | Insert 205 &CD 221 &DD 237 &ED 253 &FD 20 | Pause 196 &C4 196 &C4 244 &F4 244 &F4 21 | Delete 127 &7F 215 &D7 231 &E7 247 &F7 22 | Home 30 &1E 216 &D8 232 &E8 248 &F8 23 | PgUp 159 &9F 143 &8F 191 &BF 175 &AF 24 | PgDn 158 &9E 142 &8E 190 &BE 174 &AE 25 | 26 | PrtSc is redefinable with *KEY0 27 | 28 | 29 | The following keys change depending on *FX4 value. 30 | *FX4,0 (and *FX4,2 if not redefined with *KEY): 31 | Key Normal value Shifted value CTRL value Shift-CTRL 32 | End 139 &8B 155 &9B 171 &AB 187 &BB 33 | Left 140 &8C 156 &9C 172 &AC 188 &BC 34 | Right 141 &8D 157 &9D 173 &AD 189 &BD 35 | Down 142 &8E 158 &9E 174 &AE 190 &BE 36 | Up 143 &8F 159 &9F 175 &AF 191 &BF 37 | 38 | *FX4,1 (matches BBC Micro, End is mapped to Copy): 39 | Key Normal value 40 | End 135 &87 41 | Left 136 &88 42 | Right 137 &89 43 | Down 138 &8A 44 | Up 139 &8B 45 | Values with modifier keys are not changed by *FX4,1. On the BBC Micro and 46 | Master, the modifier keys have no effect. 47 | -------------------------------------------------------------------------------- /src/keyboard.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Matrix Brandy Basic VI Interpreter. 3 | ** Copyright (C) 2000-2014 David Daniels 4 | ** Copyright (C) 2018-2024 Michael McConnell and contributors 5 | ** 6 | ** Brandy is free software; you can redistribute it and/or modify 7 | ** it under the terms of the GNU General Public License as published by 8 | ** the Free Software Foundation; either version 2, or (at your option) 9 | ** any later version. 10 | ** 11 | ** Brandy is distributed in the hope that it will be useful, 12 | ** but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | ** GNU General Public License for more details. 15 | ** 16 | ** You should have received a copy of the GNU General Public License 17 | ** along with Brandy; see the file COPYING. If not, write to 18 | ** the Free Software Foundation, 59 Temple Place - Suite 330, 19 | ** Boston, MA 02111-1307, USA. 20 | ** 21 | ** 22 | ** This file defines the keyboard handling routines 23 | */ 24 | 25 | #ifndef __keyboard_h 26 | #define __keyboard_h 27 | 28 | #include "common.h" 29 | 30 | typedef enum {READ_OK, READ_ESC, READ_EOF} readstate; 31 | // This is original source of BGET at EOF giving &FE: 32 | // -0 -1 -2 33 | // 000000:00 FFFFFF:FF FFFFFF:FE 34 | 35 | extern int32 read_key(void); 36 | extern void set_escint(int i); 37 | extern void set_escmul(int i); 38 | extern void kbd_setvikeys(int x); 39 | extern readstate emulate_readline(char [], int32, int32); 40 | extern void purge_keys(void); 41 | #ifdef TARGET_RISCOS 42 | extern char *get_fn_string(int key, int *len); 43 | extern int set_fn_string(int key, char *string, int length); 44 | #endif /* TARGET_RISCOS */ 45 | extern boolean kbd_init(); 46 | extern void kbd_quit(void); 47 | extern int32 kbd_get(void); 48 | extern int32 kbd_get0(void); 49 | extern int32 kbd_inkey(int32); 50 | #ifdef TARGET_RISCOS 51 | extern int32 kbd_inkey256(void); 52 | #endif /* TARGET_RISCOS */ 53 | extern int32 kbd_modkeys(int32); 54 | extern int kbd_fnkeyset(int key, char *string, int length); 55 | extern char *kbd_fnkeyget(int key, int *length); 56 | extern int32 kbd_readline(char *buffer, int32 length, int32 chars); 57 | extern int32 kbd_buffered(void); 58 | extern int32 kbd_pending(void); 59 | extern void kbd_escchar(char, char); 60 | extern int kbd_escpoll(void); 61 | extern int kbd_esctest(void); 62 | extern int kbd_escack(void); 63 | extern void push_key(int32 ch); 64 | extern void osbyte21(int32 xreg); 65 | #endif /* __keyboard_h */ 66 | -------------------------------------------------------------------------------- /docs/banana-bugs.txt: -------------------------------------------------------------------------------- 1 | Banana Brandy update v1.20/v0.02 2 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 3 | BEAT and BEATS seperated, they do two different things. 4 | BEAT reads current microbeat number, BEATS reads total number 5 | of microbeats in a bar. 6 | 7 | tokens.c/editor.c 8 | ----------------- 9 | Can load Russell format BASIC programs (Z80/DOS/Windows BASIC). 10 | 11 | mos.c 12 | ----- 13 | All mos_oscli() functions combined together. 14 | CALL OSBYTE and OSWORD on RISC OS passed directly to OS_Byte and OS_Word. 15 | 16 | 17 | Apple Brandy update v1.20/v0.01 18 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 19 | error.c 20 | ------- 21 | Fixed some ERR error numbers. Added OSCLI error messages. 22 | Fixed REPORT and default error reporter to output \r\n before message. 23 | 24 | keyboard.c 25 | ---------- 26 | Handles zero-length function key strings correctly. 27 | 28 | statement.s 29 | ----------- 30 | Executing DEF correctly skips past to next line, allowing correct execution 31 | of, multiple-entry procedures, eg: 32 | 10 DEFPROCtimed(delay%) 33 | 20 DEFPROCdefault:LOCAL delay%:delay%=100 34 | 30 delay%=TIME+delay%:REPEAT UNTIL TIME>delay%:ENDPROC 35 | 36 | Renamed emulate.c and emulate.h to mos.c and mos.h 37 | -------------------------------------------------- 38 | 39 | mos.c 40 | ----- 41 | OSCLI passed to OS restores text cursor to next line after any output. 42 | Rewritten *FX to correctly parse numbers and call OSBYTE. 43 | Added mos_osbyte() to provide low-level OSBYTE functions. Serial 44 | handling FXs translated to OSBYTEs and renumbered to correct OSBYTE 45 | calls. 46 | 47 | Written cmd_parse_dec() for *FX and *KEY and any other future commands. 48 | 49 | Added *HELP with help topics. See *HELP BASIC, *HELP MOS. 50 | 51 | *KEY rewritten, with generalised gstrans() function. 52 | 53 | Need to write proper command table parser to replace command_check(). 54 | 55 | 56 | Bugs identified to be fixed 57 | =========================== 58 | GSTrans terminates at a quote when it shouldn't, eg 59 | *KEY 1 hello"there 60 | should assign the string hello"there but instead assigns hello". 61 | 62 | When sys_font[] is available, implement OSWORD 10 to read font bitmap. 63 | 64 | Need to add *LOAD and *SAVE commands. 65 | 66 | Integrate extensions from WinCE fork (^variable, SYS to host OS, etc.) 67 | Add $$ to reference null-terminated strings. 68 | Move toupper()/tolower() to in-code functions, removes need for UnixLib 69 | on RISC OS. 70 | Probably need host-specific modules for SYS calls. 71 | Make *FX0,0 give appropriate error string. 72 | RISC OS Brandy should be able to claim memory on startup instead of needing 73 | *WimpSlot beforehand. 74 | *cd doesn't give any error. 75 | MinGW: Escape causes next char to also be Escape. 76 | -------------------------------------------------------------------------------- /docs/raspi-gpio.txt: -------------------------------------------------------------------------------- 1 | Raspberry Pi GPIO support 2 | ========================= 3 | 4 | RISC OS note: Under RISC OS, the GPIO module provides support in the GPIO_ 5 | namespace, the RaspberryPi_ namespace is not supported. 6 | 7 | In keeping with the BBC Micro style of I/O ports being memory-mapped, if 8 | Brandy is able to open /dev/gpiomem for read-write, then it'll mmap() it, 9 | and the following code can be used to test whether it's available, and if 10 | so, where. 11 | 12 | SYS "RaspberryPi_GPIOInfo" TO present%,gpiomem% 13 | 14 | If /dev/gpiomem is available and usable, present% will be set to 1, and 15 | gpiomem% set to the base of memory as addressed within Brandy. Otherwise, 16 | present% will be set to 0, and gpiomem% to &FFFFFFFF. This will happen every 17 | time Matrix Brandy is started. 18 | 19 | With the exception of the above SYS call, all the other GPIO calls report the 20 | error "Raspberry Pi GPIO not available" if present% is 0 (and it wasn't 21 | called as an X call). 22 | 23 | The remaining SYS calls all take the GPIO port number in R0 and the 24 | parameter, if required, in R1. Those that return a value do so in R0. 25 | 26 | The other GPIO calls are: 27 | RaspberryPi_GetGPIOPortMode: R0=port 28 | Returns a value from 0 to 7: 29 | 0: Input 30 | 1: Output 31 | 2: ALT5 32 | 3: ALT4 33 | 4: ALT0 34 | 5: ALT1 35 | 6: ALT2 36 | 7: ALT3 37 | 38 | RaspberryPi_SetGPIOPortMode: R0=port, R1=mode (as above). 39 | 40 | RaspberryPi_SetGPIOPortPullUpDownMode: R0=port, R1=mode 41 | 0: Off 42 | 1: Down 43 | 2: Up 44 | 45 | RaspberryPi_ReadGPIOPort: R0=port. Value returned in R0. 46 | 47 | RaspberryPi_WriteGPIOPort: R0=port, R1=value 48 | 49 | As an alternative to the SYS calls, a slightly modified version of BBCSDL's 50 | gpiolib.bbc by Richard Russell should also work, with the following change: 51 | Replace FN_gpio_setup with the following: 52 | DEF FN_gpio_setup 53 | LOCAL present% 54 | SYS "RaspberryPi_GPIOInfo" TO present%,G% 55 | IF present%=0 THEN ERROR 0, "GPIO not present or usable" 56 | = G% 57 | 58 | Also - SOME SWIs from the RISC OS GPIO module are implemented. At this point, 59 | the following are: 60 | GPIO_GetBoard 61 | Returns board model code local to the module in R0, 62 | the board type string in R1 63 | and additionally, local to Brandy, the 32-bit model code from /proc/cpuinfo 64 | into R2. 65 | GPIO_ReadMode: mapped to RaspberryPi_GetGPIOPortMode 66 | GPIO_WriteMode: mapped to RaspberryPi_SetGPIOPortMode 67 | GPIO_ReadData: mapped to RaspberryPi_ReadGPIOPort 68 | GPIO_WriteData: mapped to RaspberryPi_WriteGPIOPort 69 | -------------------------------------------------------------------------------- /makefile.text: -------------------------------------------------------------------------------- 1 | # Makefile for brandy in text mode under NetBSD and Linux 2 | 3 | CC = gcc 4 | LD = gcc 5 | STRIP = strip 6 | ADDFLAGS = ${BRANDY_BUILD_FLAGS} 7 | 8 | include build/git.mk 9 | 10 | #CFLAGS = -g -DDEBUG -I/usr/include/SDL -DNO_SDL -DDEFAULT_IGNORE -Wall $(GITFLAGS) $(ADDFLAGS) 11 | #CFLAGS = -g -I/usr/include/SDL -DNO_SDL -DDEFAULT_IGNORE -Wall $(GITFLAGS) $(ADDFLAGS) 12 | CFLAGS = -O3 -fPIE -I/usr/include/SDL -DNO_SDL -DDEFAULT_IGNORE -Wall $(GITFLAGS) $(ADDFLAGS) 13 | 14 | LDFLAGS = 15 | 16 | LIBS = -lm -ldl -lpthread -lrt 17 | 18 | SRCDIR = src 19 | 20 | OBJ = $(SRCDIR)/variables.o $(SRCDIR)/tokens.o \ 21 | $(SRCDIR)/strings.o $(SRCDIR)/statement.o $(SRCDIR)/stack.o \ 22 | $(SRCDIR)/miscprocs.o $(SRCDIR)/mainstate.o $(SRCDIR)/lvalue.o \ 23 | $(SRCDIR)/keyboard.o $(SRCDIR)/iostate.o $(SRCDIR)/heap.o \ 24 | $(SRCDIR)/functions.o $(SRCDIR)/fileio.o $(SRCDIR)/evaluate.o \ 25 | $(SRCDIR)/errors.o $(SRCDIR)/mos.o $(SRCDIR)/editor.o \ 26 | $(SRCDIR)/convert.o $(SRCDIR)/commands.o $(SRCDIR)/brandy.o \ 27 | $(SRCDIR)/assign.o $(SRCDIR)/net.o $(SRCDIR)/mos_sys.o 28 | 29 | TEXTONLYOBJ = $(SRCDIR)/textonly.o 30 | 31 | SIMPLETEXTOBJ = $(SRCDIR)/simpletext.o 32 | 33 | SRC = $(SRCDIR)/variables.c $(SRCDIR)/tokens.c \ 34 | $(SRCDIR)/strings.c $(SRCDIR)/statement.c $(SRCDIR)/stack.c \ 35 | $(SRCDIR)/miscprocs.c $(SRCDIR)/mainstate.c $(SRCDIR)/lvalue.c \ 36 | $(SRCDIR)/keyboard.c $(SRCDIR)/iostate.c $(SRCDIR)/heap.c \ 37 | $(SRCDIR)/functions.c $(SRCDIR)/fileio.c $(SRCDIR)/evaluate.c \ 38 | $(SRCDIR)/errors.c $(SRCDIR)/mos.c $(SRCDIR)/editor.c \ 39 | $(SRCDIR)/convert.c $(SRCDIR)/commands.c $(SRCDIR)/brandy.c \ 40 | $(SRCDIR)/assign.c $(SRCDIR)/net.c $(SRCDIR)/mos_sys.c 41 | 42 | TEXTONLYSRC = $(SRCDIR)/textonly.c 43 | 44 | SIMPLETEXTSRC = $(SRCDIR)/simpletext.c 45 | 46 | all: tbrandy sbrandy 47 | 48 | tbrandy: $(OBJ) $(TEXTONLYOBJ) 49 | @echo "" 50 | @echo "Build flags: $(CFLAGS)" 51 | $(LD) $(LDFLAGS) -o tbrandy $(OBJ) $(TEXTONLYOBJ) $(LIBS) 52 | 53 | sbrandy: $(OBJ) $(SIMPLETEXTOBJ) 54 | @echo "" 55 | $(LD) $(LDFLAGS) -o sbrandy $(OBJ) $(SIMPLETEXTOBJ) $(LIBS) 56 | 57 | include build/depends.mk 58 | 59 | .c.o: 60 | @echo -n "$@ " 61 | @$(CC) $(CFLAGS) $< -c -o $@ 62 | 63 | trecompile: 64 | $(CC) $(CFLAGS) $(SRC) $(TEXTONLYSRC) $(LIBS) -o tbrandy 65 | 66 | srecompile: 67 | $(CC) $(CFLAGS) $(SRC) $(SIMPLETEXTSRC) $(LIBS) -o sbrandy 68 | 69 | tnodebug: 70 | $(CC) $(CFLAGS2) $(SRC) $(TEXTONLYSRC) $(LIBS) -o tbrandy 71 | $(STRIP) tbrandy 72 | 73 | snodebug: 74 | $(CC) $(CFLAGS2) $(SRC) $(SIMPLETEXTSRC) $(LIBS) -o sbrandy 75 | $(STRIP) sbrandy 76 | 77 | tcheck: 78 | $(CC) $(CFLAGS) -Wall -O2 $(SRC) $(TEXTONLYSRC) $(LIBS) -o tbrandy 79 | 80 | scheck: 81 | $(CC) $(CFLAGS) -Wall -O2 $(SRC) $(SIMPLETEXTSRC) $(LIBS) -o sbrandy 82 | 83 | clean: 84 | rm -f $(SRCDIR)/*.o tbrandy sbrandy 85 | 86 | test: sbrandy 87 | prove -r t/ 88 | -------------------------------------------------------------------------------- /makefile: -------------------------------------------------------------------------------- 1 | # Makefile for brandy under NetBSD and Linux 2 | 3 | CC = gcc 4 | LD = gcc 5 | STRIP = strip 6 | ADDFLAGS = ${BRANDY_BUILD_FLAGS} 7 | 8 | include build/git.mk 9 | 10 | #CFLAGS = -g -DDEBUG $(shell sdl-config --cflags) -I/usr/local/include/SDL -DUSE_SDL -DDEFAULT_IGNORE -Wall $(GITFLAGS) $(ADDFLAGS) 11 | #CFLAGS = -g $(shell sdl-config --cflags) -I/usr/local/include/SDL -DUSE_SDL -DDEFAULT_IGNORE -Wall $(GITFLAGS) $(ADDFLAGS) 12 | CFLAGS = -O3 -fPIE $(shell sdl-config --cflags) -DUSE_SDL -DDEFAULT_IGNORE -Wall $(GITFLAGS) $(ADDFLAGS) 13 | 14 | LDFLAGS += 15 | 16 | LIBS = -lm $(shell sdl-config --libs) -ldl -pthread -lrt -lX11 17 | 18 | SRCDIR = src 19 | 20 | OBJ = \ 21 | $(SRCDIR)/evaluate.o \ 22 | $(SRCDIR)/graphsdl.o \ 23 | $(SRCDIR)/assign.o \ 24 | $(SRCDIR)/mainstate.o \ 25 | $(SRCDIR)/tokens.o \ 26 | $(SRCDIR)/mos.o \ 27 | $(SRCDIR)/commands.o \ 28 | $(SRCDIR)/functions.o \ 29 | $(SRCDIR)/iostate.o \ 30 | $(SRCDIR)/variables.o \ 31 | $(SRCDIR)/fileio.o \ 32 | $(SRCDIR)/soundsdl.o \ 33 | $(SRCDIR)/keyboard.o \ 34 | $(SRCDIR)/miscprocs.o \ 35 | $(SRCDIR)/editor.o \ 36 | $(SRCDIR)/stack.o \ 37 | $(SRCDIR)/mos_sys.o \ 38 | $(SRCDIR)/strings.o \ 39 | $(SRCDIR)/lvalue.o \ 40 | $(SRCDIR)/errors.o \ 41 | $(SRCDIR)/convert.o \ 42 | $(SRCDIR)/brandy.o \ 43 | $(SRCDIR)/statement.o \ 44 | $(SRCDIR)/net.o \ 45 | $(SRCDIR)/heap.o 46 | 47 | SRC = \ 48 | $(SRCDIR)/evaluate.c \ 49 | $(SRCDIR)/graphsdl.c \ 50 | $(SRCDIR)/assign.c \ 51 | $(SRCDIR)/mainstate.c \ 52 | $(SRCDIR)/tokens.c \ 53 | $(SRCDIR)/mos.c \ 54 | $(SRCDIR)/commands.c \ 55 | $(SRCDIR)/functions.c \ 56 | $(SRCDIR)/iostate.c \ 57 | $(SRCDIR)/variables.c \ 58 | $(SRCDIR)/fileio.c \ 59 | $(SRCDIR)/soundsdl.c \ 60 | $(SRCDIR)/keyboard.c \ 61 | $(SRCDIR)/miscprocs.c \ 62 | $(SRCDIR)/editor.c \ 63 | $(SRCDIR)/stack.c \ 64 | $(SRCDIR)/mos_sys.c \ 65 | $(SRCDIR)/strings.c \ 66 | $(SRCDIR)/lvalue.c \ 67 | $(SRCDIR)/errors.c \ 68 | $(SRCDIR)/convert.c \ 69 | $(SRCDIR)/brandy.c \ 70 | $(SRCDIR)/statement.c \ 71 | $(SRCDIR)/net.c \ 72 | $(SRCDIR)/heap.c 73 | 74 | brandy: $(OBJ) 75 | @echo "" 76 | @echo "Build flags: $(CFLAGS)" 77 | $(LD) $(LDFLAGS) -o brandy $(OBJ) $(LIBS) 78 | 79 | include build/depends.mk 80 | 81 | .c.o:; @echo -n "$@ " 82 | @$(CC) $(CFLAGS) $< -c -o $@ >/dev/null 83 | 84 | recompile: 85 | $(CC) $(CFLAGS) $(SRC) $(LIBS) -o brandy 86 | 87 | nodebug: 88 | $(CC) $(CFLAGS2) $(SRC) $(LIBS) -o brandy 89 | $(STRIP) brandy 90 | 91 | check: 92 | $(CC) $(CFLAGS) -Wall -O2 $(SRC) $(LIBS) -o brandy 93 | 94 | clean: 95 | rm -f $(SRCDIR)/*.o brandy 96 | 97 | cleanall: 98 | rm -f $(SRCDIR)/*.o brandy sbrandy tbrandy 99 | 100 | text: 101 | $(MAKE) -f makefile.text 102 | 103 | textclean: 104 | rm -f $(SRCDIR)/*.o sbrandy tbrandy 105 | 106 | all: brandy 107 | 108 | -------------------------------------------------------------------------------- /makefile.mingw-sdl: -------------------------------------------------------------------------------- 1 | # Makefile for brandy under Windows x86 / x64 with MinGW using Cygwin as the 2 | # toolchain 3 | 4 | # Find MinGW gcc 5 | compiler=$(shell which i686-w64-mingw32-gcc.exe 2>/dev/null) 6 | MINGWPATH=/usr/i686-w64-mingw32/sys-root/mingw 7 | ifeq ($(compiler),) 8 | compiler=$(shell which x86_64-w64-mingw32-gcc.exe 2>/dev/null) 9 | MINGWPATH=/usr/x86_64-w64-mingw32/sys-root/mingw 10 | ifeq ($(compiler),) 11 | $(error Unable to find MinGW gcc compiler) 12 | endif 13 | endif 14 | 15 | CC = $(compiler) 16 | LD = $(compiler) 17 | STRIP = strip 18 | ADDFLAGS = ${BRANDY_BUILD_FLAGS} 19 | 20 | include build/git.mk 21 | 22 | #CFLAGS = -g -DDEBUG -I$(MINGWPATH)/include/SDL -DUSE_SDL -DCYGWINBUILD -DDEFAULT_IGNORE -D__USE_MINGW_ANSI_STDIO=1 -Wall $(ADDFLAGS) 23 | #CFLAGS = -g -I$(MINGWPATH)/include/SDL -DUSE_SDL -DCYGWINBUILD -DDEFAULT_IGNORE -D__USE_MINGW_ANSI_STDIO=1 -Wall $(GITFLAGS) $(ADDFLAGS) 24 | CFLAGS = -O3 -I$(MINGWPATH)/include/SDL -DUSE_SDL -DCYGWINBUILD -DDEFAULT_IGNORE -D__USE_MINGW_ANSI_STDIO=1 -Wall $(GITFLAGS) $(ADDFLAGS) 25 | 26 | LDFLAGS += 27 | 28 | LIBS = -lm $(MINGWPATH)/lib/libSDL.a -lws2_32 -mwindows $(MINGWPATH)/lib/libdxguid.a $(MINGWPATH)/lib/libwinmm.a $(MINGWPATH)/lib/libdl.a $(MINGWPATH)/lib/libpsapi.a $(MINGWPATH)/lib/libwinpthread.a 29 | 30 | SRCDIR = src 31 | 32 | OBJ = $(SRCDIR)/variables.o $(SRCDIR)/tokens.o $(SRCDIR)/graphsdl.o \ 33 | $(SRCDIR)/strings.o $(SRCDIR)/statement.o $(SRCDIR)/stack.o \ 34 | $(SRCDIR)/miscprocs.o $(SRCDIR)/mainstate.o $(SRCDIR)/lvalue.o \ 35 | $(SRCDIR)/keyboard.o $(SRCDIR)/iostate.o $(SRCDIR)/heap.o \ 36 | $(SRCDIR)/functions.o $(SRCDIR)/fileio.o $(SRCDIR)/evaluate.o \ 37 | $(SRCDIR)/errors.o $(SRCDIR)/mos.o $(SRCDIR)/editor.o \ 38 | $(SRCDIR)/convert.o $(SRCDIR)/commands.o $(SRCDIR)/brandy.o \ 39 | $(SRCDIR)/assign.o $(SRCDIR)/net.o $(SRCDIR)/mos_sys.o \ 40 | $(SRCDIR)/soundsdl.o 41 | 42 | SRC = $(SRCDIR)/variables.c $(SRCDIR)/tokens.c $(SRCDIR)/graphsdl.c \ 43 | $(SRCDIR)/strings.c $(SRCDIR)/statement.c $(SRCDIR)/stack.c \ 44 | $(SRCDIR)/miscprocs.c $(SRCDIR)/mainstate.c $(SRCDIR)/lvalue.c \ 45 | $(SRCDIR)/keyboard.c $(SRCDIR)/iostate.c $(SRCDIR)/heap.c \ 46 | $(SRCDIR)/functions.c $(SRCDIR)/fileio.c $(SRCDIR)/evaluate.c \ 47 | $(SRCDIR)/errors.c $(SRCDIR)/mos.c $(SRCDIR)/editor.c \ 48 | $(SRCDIR)/convert.c $(SRCDIR)/commands.c $(SRCDIR)/brandy.c \ 49 | $(SRCDIR)/assign.c $(SRCDIR)/net.c $(SRCDIR)/mos_sys.c \ 50 | $(SRCDIR)/soundsdl.c 51 | 52 | brandy: $(OBJ) 53 | $(LD) $(LDFLAGS) -o brandy $(OBJ) $(LIBS) 54 | 55 | include build/depends.mk 56 | 57 | .c.o: 58 | $(CC) $(CFLAGS) $< -c -o $@ 59 | 60 | recompile: 61 | $(CC) $(CFLAGS) $(SRC) $(LIBS) -o brandy 62 | 63 | nodebug: 64 | $(CC) $(CFLAGS2) $(SRC) $(LIBS) -o brandy 65 | $(STRIP) brandy 66 | 67 | check: 68 | $(CC) $(CFLAGS) -Wall -O2 $(SRC) $(LIBS) -o brandy 69 | 70 | clean: 71 | rm -f $(SRCDIR)/*.o brandy.exe 72 | 73 | all: brandy 74 | -------------------------------------------------------------------------------- /examples/testEllipse: -------------------------------------------------------------------------------- 1 | 10REM >testEllipse 2 | 20MODE 12 3 | 30ORIGIN640,512 4 | 40SX%=80:REM this is the side point of the ellipse (i.e. x-axis intercept) 5 | 50OX%=0:OY%=0:OB%=0 6 | 60MOUSE ON 7 | 70REPEAT 8 | 80MOUSE X%,Y%,B% 9 | 90IF X%<>OX% OR Y%<>OY% OR B%<>OB% THEN 10 | 100CLS 11 | 110PRINT"Green ellipse tests ELLIPSE FILL command. Blue lines show major/minor axes." 12 | 120PRINT"White ellipses are PLOT 205 (filled) and PLOT197 (outline)" 13 | 130PRINT"Red lines show PLOT205 control points. All 3 ellipses should be parallel." 14 | 140PRINT"Click and hold mouse to shift x-axis control point" 15 | 150GCOL0,7:REM white 16 | 160MOVE 0,0:REM centre of ellipse 17 | 170MOVE SX%*1.2,0:REM side point of ellipse (i.e. x-axis intercept) 18 | 180IF B%<>0 SX%=X% 19 | 190PLOT 197,X%*1.2,Y%*1.2:REM Top point of ellipse; draw ellipse outline 20 | 200 21 | 210MOVE 0,0:REM centre of ellipse 22 | 220MOVE SX%,0:REM side point of ellipse (i.e. x-axis intercept) 23 | 230PLOT 205,X%,Y% :REM Top point of ellipse; draw filled ellipse 24 | 240 25 | 250IF Y%<>0 AND SX%<>0 THEN 26 | 260REM Test the ELLIPSE FILL cx,cy,major,minor,angle command. 27 | 270REM To test this, we need to convert the plot 197 control points into major and minor axis lengths, plus a rotation angle alpha for the ellipse 28 | 280REM First convert the ellipse into a more familiar Cartesian form, Ax^2+Bxy+Cy^2=1 29 | 290REM on x axis, y=0, so Cartesian form simplifies to Ax^2=1. Solve for A... 30 | 300A=1/SX%^2 31 | 310REM at top of ellipse, dy/dx=0, so -2xA-By=0, so use this to find B: 32 | 320B=2*X%*A/-Y% 33 | 330REM Use fact that the cartesian curve passes through (X%,Y%) and solve for C 34 | 340C=(1-A*X%^2-B*X%*Y%)/Y%^2 35 | 350REM calc ellipse angle, using formulae on https://en.wikipedia.org/wiki/Ellipse#General_ellipse with D=0,E=0,F=-1 36 | 360alpha=ATN(-B,C-A)/2:REM in matrix brandy, ATN(a,b) implements atan2 function. 37 | 370REM calc major + minor axis lengths, using formulae on https://en.wikipedia.org/wiki/Ellipse#General_ellipse with D=0,E=0,F=-1 38 | 380major=-SQR(-2*(B^2-4*A*C)*((A+C)+SQR((A-C)^2+B^2)))/(B^2-4*A*C) 39 | 390minor=-SQR(-2*(B^2-4*A*C)*((A+C)-SQR((A-C)^2+B^2)))/(B^2-4*A*C) 40 | 400REM now we have ellipse in major,minor,alpha form, we can use the ELLIPSE FILL command and check it produces an aligned ellipse. 41 | 410GCOL0,2:REM green 42 | 420ELLIPSE FILL 0,0,major*0.8,minor*0.8,alpha 43 | 430GCOL0,4:REM blue. Draw major and minor axes... 44 | 440LINE -major*0.8*COS(alpha), -major*0.8*SIN(alpha), major*0.8*COS(alpha), major*0.8*SIN(alpha) 45 | 450LINE +minor*0.8*SIN(alpha), -minor*0.8*COS(alpha),-minor*0.8*SIN(alpha), minor*0.8*COS(alpha) 46 | 460ENDIF 47 | 470 48 | 480GCOL 0,1:REM red. Draw control points for white ellipse... 49 | 490LINE 0,0,SX%,0 50 | 500LINE 0,0,X%,Y% 51 | 510 52 | 520OX%=X%:OY%=Y%:OB%=B% 53 | 530WAIT 54 | 540ENDIF 55 | 550WAIT 56 | 560UNTIL FALSE 57 | -------------------------------------------------------------------------------- /src/mainstate.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Matrix Brandy Basic VI Interpreter. 3 | ** Copyright (C) 2000-2014 David Daniels 4 | ** Copyright (C) 2018-2024 Michael McConnell and contributors 5 | ** 6 | ** Brandy is free software; you can redistribute it and/or modify 7 | ** it under the terms of the GNU General Public License as published by 8 | ** the Free Software Foundation; either version 2, or (at your option) 9 | ** any later version. 10 | ** 11 | ** Brandy is distributed in the hope that it will be useful, 12 | ** but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | ** GNU General Public License for more details. 15 | ** 16 | ** You should have received a copy of the GNU General Public License 17 | ** along with Brandy; see the file COPYING. If not, write to 18 | ** the Free Software Foundation, 59 Temple Place - Suite 330, 19 | ** Boston, MA 02111-1307, USA. 20 | ** 21 | ** 22 | ** This file defines the functions that handle all the Basic 23 | ** statement types apart from assignments and I/O statements 24 | */ 25 | 26 | #ifndef __mainstate_h 27 | #define __mainstate_h 28 | 29 | extern void exec_assembler(void); 30 | extern void exec_asmend(void); 31 | extern void exec_oscmd(void); 32 | extern void exec_call(void); 33 | extern void exec_case(void); 34 | extern void exec_xcase(void); 35 | extern void exec_chain(void); 36 | extern void exec_clear(void); 37 | extern void exec_data(void); 38 | extern void exec_def(void); 39 | extern void exec_dim(void); 40 | extern void exec_elsewhen(void); 41 | extern void exec_xelse(void); 42 | extern void exec_xlhelse(void); 43 | extern void exec_end(void); 44 | extern void exec_endifcase(void); 45 | extern void exec_endproc(void); 46 | extern void exec_fnreturn(void); 47 | extern void exec_endwhile(void); 48 | extern void exec_error(void); 49 | extern void exec_exit(void); 50 | extern void exec_for(void); 51 | extern void exec_gosub(void); 52 | extern void exec_goto(void); 53 | extern void exec_blockif(void); 54 | extern void exec_singlif(void); 55 | extern void exec_xif(void); 56 | extern void exec_let(void); 57 | extern void exec_library(void); 58 | extern void exec_local(void); 59 | extern void exec_next(void); 60 | extern void exec_on(void); 61 | extern void exec_oscli(void); 62 | extern void exec_overlay(void); 63 | extern void exec_proc(void); 64 | extern void exec_xproc(void); 65 | extern void exec_quit(void); 66 | extern void exec_read(void); 67 | extern void exec_rem(void); 68 | extern void exec_repeat(void); 69 | extern void exec_report(void); 70 | extern void exec_restore(void); 71 | extern void exec_return(void); 72 | extern void exec_run(void); 73 | extern void exec_stop(void); 74 | extern void exec_swap(void); 75 | extern void exec_sys(void); 76 | extern void exec_trace(void); 77 | extern void exec_until(void); 78 | extern void exec_wait(void); 79 | extern void exec_xwhen(void); 80 | extern void exec_while(void); 81 | 82 | #endif 83 | -------------------------------------------------------------------------------- /makefile.app.mingw-sdl: -------------------------------------------------------------------------------- 1 | # Makefile for brandy under Windows x86 / x64 with MinGW using Cygwin as the 2 | # toolchain 3 | 4 | # Find MinGW gcc 5 | compiler=$(shell which i686-w64-mingw32-gcc.exe 2>/dev/null) 6 | MINGWPATH=/usr/i686-w64-mingw32/sys-root/mingw 7 | ifeq ($(compiler),) 8 | compiler=$(shell which x86_64-w64-mingw32-gcc.exe 2>/dev/null) 9 | MINGWPATH=/usr/x86_64-w64-mingw32/sys-root/mingw 10 | ifeq ($(compiler),) 11 | $(error Unable to find MinGW gcc compiler) 12 | endif 13 | endif 14 | 15 | CC = $(compiler) 16 | LD = $(compiler) 17 | STRIP = strip 18 | ADDFLAGS = ${BRANDY_BUILD_FLAGS} 19 | 20 | include build/git.mk 21 | 22 | #CFLAGS = -g -DDEBUG -I$(MINGWPATH)/include/SDL -DUSE_SDL -DCYGWINBUILD -DDEFAULT_IGNORE -DBRANDYAPP -D__USE_MINGW_ANSI_STDIO=1 -Wall $(GITFLAGS) $(ADDFLAGS) 23 | #CFLAGS = -g -I$(MINGWPATH)/include/SDL -DUSE_SDL -DCYGWINBUILD -DDEFAULT_IGNORE -DBRANDYAPP -D__USE_MINGW_ANSI_STDIO=1 -Wall $(GITFLAGS) $(ADDFLAGS) 24 | CFLAGS = -O3 -I$(MINGWPATH)/include/SDL -DUSE_SDL -DCYGWINBUILD -DDEFAULT_IGNORE -DBRANDYAPP -D__USE_MINGW_ANSI_STDIO=1 -Wall $(GITFLAGS) $(ADDFLAGS) 25 | 26 | LDFLAGS += 27 | 28 | LIBS = -lm $(MINGWPATH)/lib/libSDL.a -lws2_32 -mwindows $(MINGWPATH)/lib/libdxguid.a $(MINGWPATH)/lib/libwinmm.a $(MINGWPATH)/lib/libdl.a $(MINGWPATH)/lib/libpsapi.a $(MINGWPATH)/lib/libwinpthread.a 29 | 30 | SRCDIR = src 31 | 32 | OBJ = $(SRCDIR)/variables.o $(SRCDIR)/tokens.o $(SRCDIR)/graphsdl.o \ 33 | $(SRCDIR)/strings.o $(SRCDIR)/statement.o $(SRCDIR)/stack.o \ 34 | $(SRCDIR)/miscprocs.o $(SRCDIR)/mainstate.o $(SRCDIR)/lvalue.o \ 35 | $(SRCDIR)/keyboard.o $(SRCDIR)/iostate.o $(SRCDIR)/heap.o \ 36 | $(SRCDIR)/functions.o $(SRCDIR)/fileio.o $(SRCDIR)/evaluate.o \ 37 | $(SRCDIR)/errors.o $(SRCDIR)/mos.o $(SRCDIR)/editor.o \ 38 | $(SRCDIR)/convert.o $(SRCDIR)/commands.o $(SRCDIR)/brandy.o \ 39 | $(SRCDIR)/assign.o $(SRCDIR)/net.o $(SRCDIR)/mos_sys.o \ 40 | $(SRCDIR)/soundsdl.o $(SRCDIR)/app.o 41 | 42 | SRC = $(SRCDIR)/variables.c $(SRCDIR)/tokens.c $(SRCDIR)/graphsdl.c \ 43 | $(SRCDIR)/strings.c $(SRCDIR)/statement.c $(SRCDIR)/stack.c \ 44 | $(SRCDIR)/miscprocs.c $(SRCDIR)/mainstate.c $(SRCDIR)/lvalue.c \ 45 | $(SRCDIR)/keyboard.c $(SRCDIR)/iostate.c $(SRCDIR)/heap.c \ 46 | $(SRCDIR)/functions.c $(SRCDIR)/fileio.c $(SRCDIR)/evaluate.c \ 47 | $(SRCDIR)/errors.c $(SRCDIR)/mos.c $(SRCDIR)/editor.c \ 48 | $(SRCDIR)/convert.c $(SRCDIR)/commands.c $(SRCDIR)/brandy.c \ 49 | $(SRCDIR)/assign.c $(SRCDIR)/net.c $(SRCDIR)/mos_sys.c \ 50 | $(SRCDIR)/soundsdl.c $(SRCDIR)/app.c 51 | 52 | brandyapp: $(OBJ) 53 | $(LD) $(LDFLAGS) -o brandyapp $(OBJ) $(LIBS) 54 | 55 | include build/depends.mk 56 | 57 | .c.o: 58 | $(CC) $(CFLAGS) $< -c -o $@ 59 | 60 | recompile: 61 | $(CC) $(CFLAGS) $(SRC) $(LIBS) -o brandy 62 | 63 | nodebug: 64 | $(CC) $(CFLAGS2) $(SRC) $(LIBS) -o brandy 65 | $(STRIP) brandyapp.exe 66 | 67 | check: 68 | $(CC) $(CFLAGS) -Wall -O2 $(SRC) $(LIBS) -o brandyapp 69 | 70 | clean: 71 | rm -f $(SRCDIR)/*.o brandyapp.exe 72 | 73 | all: brandyapp 74 | -------------------------------------------------------------------------------- /src/miscprocs.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Matrix Brandy Basic VI Interpreter. 3 | ** Copyright (C) 2000-2014 David Daniels 4 | ** Copyright (C) 2018-2024 Michael McConnell and contributors 5 | ** 6 | ** Brandy is free software; you can redistribute it and/or modify 7 | ** it under the terms of the GNU General Public License as published by 8 | ** the Free Software Foundation; either version 2, or (at your option) 9 | ** any later version. 10 | ** 11 | ** Brandy is distributed in the hope that it will be useful, 12 | ** but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | ** GNU General Public License for more details. 15 | ** 16 | ** You should have received a copy of the GNU General Public License 17 | ** along with Brandy; see the file COPYING. If not, write to 18 | ** the Free Software Foundation, 59 Temple Place - Suite 330, 19 | ** Boston, MA 02111-1307, USA. 20 | ** 21 | ** 22 | ** Miscellaneous functions 23 | */ 24 | 25 | #ifndef __miscprocs_h 26 | #define __miscprocs_h 27 | #include 28 | 29 | #ifdef USE_SDL 30 | #include 31 | #endif 32 | 33 | #include "common.h" 34 | #include "basicdefs.h" 35 | 36 | #ifdef TARGET_RISCOS 37 | extern int64 llabs(int64); 38 | #endif 39 | extern boolean read_line(char [], int32); 40 | extern boolean amend_line(char [], int32); 41 | extern int32 get_integer(size_t); 42 | extern int64 get_int64(size_t); 43 | extern float64 get_float(size_t); 44 | extern void store_integer(size_t, int32); 45 | extern void store_int64(size_t, int64); 46 | extern void store_float(size_t, float64); 47 | #ifdef USE_SDL 48 | extern size_t m7offset(size_t); 49 | #else 50 | #define m7offset(p) (p) 51 | #endif 52 | extern char *skip_blanks(char *); 53 | extern byte *skip(byte *); 54 | extern char *tocstring(char *, int32); 55 | extern byte *find_line(int32); 56 | extern byte *find_linestart(byte *); 57 | extern library *find_library(byte *); 58 | extern void show_byte(size_t, size_t); 59 | extern void show_word(size_t, size_t); 60 | extern void save_current(void); 61 | extern void restore_current(void); 62 | extern FILE *secure_tmpnam(char []); 63 | extern int32 TOINT(float64); 64 | extern int32 INT64TO32(int64); 65 | extern int64 TOINT64(float64); 66 | extern size_t TONATIVEADDR(float64); 67 | extern void set_fpu(void); 68 | extern void decimaltocomma(char *, int32); 69 | extern int32 sgni(int64); 70 | extern int32 sgnf(float64); 71 | extern void string_zeroterm(char *); 72 | extern char *translatefname(char *); 73 | extern int32 get_listo(void); 74 | extern void set_listoption(int32); 75 | 76 | #ifndef BRANDY_HAS_STRL_FUNCTIONS 77 | extern char *my_strlcpy(char *dest, const char *src, size_t n); 78 | #endif 79 | 80 | #ifdef USE_SDL 81 | extern Uint8 mode7frame[26][40]; 82 | #endif 83 | #define ISIDSTART(ch) (isalpha(ch) || ch=='_' || ch=='`') 84 | #define ISIDCHAR(ch) (isalnum(ch) || ch=='_' || ch=='`') 85 | 86 | #define MAX(a,b) ((a > b) ? a : b) 87 | #define MIN(a,b) ((a < b) ? a : b) 88 | 89 | #endif 90 | -------------------------------------------------------------------------------- /docs/graphics.txt: -------------------------------------------------------------------------------- 1 | Graphics Support 2 | ---------------- 3 | 4 | Brandy includes limited graphics support under Linux. It includes only a 5 | subset of the facilities provided by the RISC OS VDU drivers but it should 6 | be enough for now. 7 | 8 | This document does not apply to the RISC OS builds, as all graphics are 9 | handled by the OS, and Matrix Brandy just passes the VDU codes across. 10 | 11 | The graphics support is based around SDL 1.2 12 | 13 | The graphic support includes all of the Basic graphics statements with some 14 | restrictions and a small number of the VDU 23 commands. Features such as the 15 | extended colour fill patterns are not supported. The standard RISC OS 16 | palettes in 2, 4, 16 and 256 colour modes are emulated and both colour and 17 | greyscale palettes are possible. Colour depth 16777216 is also supported for 18 | 24-bit colour. Flashing colours are not supported, they are instead shown as 19 | dimmed versions of their non-flashing counterparts. Modes can be set using 20 | either MODE , MODE or MODE , , . Any 21 | (sensible) dimensions can be supplied, and if a requested mode is not a 22 | predefined one, MODE 126 will be configured with the desired values, then 23 | selected. 24 | 25 | All available screen modes are available under X, the window will be sized 26 | accordingly. When running on a console frame buffer, only those which will 27 | fit on the console screen will be available. 28 | 29 | New display modes can be created with *NewMode, use a mode in the range 30 | 64-126. 31 | 32 | Teletext graphics are also supported in Mode 7, see docs/Mode7. 33 | 34 | Four display banks are available (except in Mode 7), they are controlled by 35 | *FX112 and FX113 as on a BBC Master or RISC OS machine. All screen modes use 36 | the primary display, so *FX112,0 is synonymous to *FX112,1, similarly for 37 | *FX113. These are also available as OSBYTE calls via CALL/USR &FFF4 and 38 | SYS "OS_Byte" (SYS 6). 39 | 40 | *REFRESH (borrowed from BB4W/BBCSDL by Richard Russell) 41 | *REFRESH One-shot refresh of the display. 42 | *REFRESH OFF Suspends updates to the display window. 43 | *REFRESH ON Resume updates to the display window, updating it with any 44 | pending changes. 45 | *REFRESH ONERROR Suspends updates to the display window until an error 46 | condition is encountered. This option is not present in 47 | BB4W/BBCSDL. 48 | This can also be set - and read - by OSBYTE &2A (42). See osbyte.txt for 49 | more details on this. 50 | 51 | Additionally to this, the "tbrandy" text-mode build, when built on a UNIX- 52 | like system (excluding Cygwin) also supports Tektronix graphics when enabled 53 | with SYS "Brandy_TekEnabled",1 and thus can output graphics when run in an 54 | xterm window or through an emulator such as Rene Richarz's Tek4010 emulator 55 | https://github.com/rricharz/Tek4010 - and, while untested, it should even 56 | run when output to real hardware. In the SDL builds, MODEs 72-75 are 57 | dimensioned to give a graphical area the same as a Tektronix system. 58 | -------------------------------------------------------------------------------- /docs/jgh-notes.txt: -------------------------------------------------------------------------------- 1 | Matrix Brandy updates by JGH 2 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 3 | 4 | Bugs identified 5 | --------------- 6 | Needs a *ESC OFF/*FX229,1 ability. - done, but still bugs. 7 | Escape state somehow being set after *FX229,0 when CHR$27 has been in buffer. 8 | KBDTest Esc+Esc should return to menu, not give an error just after *FX229. 9 | Affects: WinSDL, WinMinGW but not WinDJP. Unix not tested. 10 | Background Escape test needs to check sv_EscapeChar not physical keypress. 11 | 12 | DJPP build embeds keyboard layout of machine the binary is built on. 13 | 14 | Abbreviated *commands report errors to DOS Window, eg "K.10O. not a recognised command" 15 | No abbreviations supported at all! Fix by rewriting command parser and dispatcher. 16 | 17 | VDU(n) not returning some correct values, see: 18 | graphsdl.c 19 | simpletext.c 20 | textonly.c 21 | 22 | Unable to test in Linux with JP keyboard as can't select JP keyboard in CentOS. 23 | 24 | Fixed 25 | ----- 26 | Foreground keypresses sometimes lost on SDL - fixed by turning off background Escape polling 27 | implement EOF#0 to test KBD, test softkey expansion, pushkey, kbd buffer - done 28 | implement ADVAL-1, test just keyboard buffer (and pushkey?) - done 29 | PTR#0, EXT#0, EOF#0 give UNTRAPPABLE ERROR! - fixed 30 | PRINT blah blah ;SPCn sometimes doesn't print newline - fixed 31 | BODGE workarounds: 32 | keyboard - fixing by rewriting whole module 33 | brandy.c - DOS target tried to open GPIO ports 34 | errors.c - DOS target tries to claim non-DOS signals 35 | mos.c - waitdelay needs to use appropriate sleep/usleep/etc calls 36 | miscprocs.c - needs to use tmpnam where mkstemp does not exist - fixed 37 | DOS build will only be able to do negative INKEY for Shift/Ctrl/Alt 38 | as DOS API does not have equivalent of Windows GetAsyncKeyState. - done 39 | MODE &87 doesn't select MODE 7 - fixed 40 | DJPP: VDU 127 kills brandy - fixed, was table overrun 41 | *cd outputs blank line 42 | djpp - fixed 43 | mingw - text cursor goes awry, also with *help, etc - fixed, was tail from *. 44 | sdl - fixed 45 | *badcommand (eg *>) cursor goes awry - fixed 46 | *SHOW to list function keys - done 47 | 48 | Have these been fixed? 49 | ---------------------- 50 | DJGPP: After MODE x line wrapping fails. 51 | Non-graphics versions should default to not bombing out with errors 52 | 53 | To do 54 | ----- 55 | *FX254 option for BBfW keymap? b7-b4=keymap, b3-b0=reserved (Master sets to &0F) 56 | Document that Win8 needs specific 64-bit version of SDL.dll 57 | Should theoretically be able to build for ARM CoPro 58 | Allow background oscli, OSCLI "command &" 59 | Need *LOAD, *SAVE - done, but need generalising 60 | cli command lookup needs to use generic table, not string matching 61 | 62 | Things like 'has misled interpreter' should be 'Mistake' 63 | Eg: 64 | >jjjj 65 | Mistake 66 | > 67 | 68 | Optimise VDU dispatcher, should have single VDU queue collector that dispatches 69 | to individual VDU support code, instead of VDU queue collector duplicated in 70 | every single VDU module. 71 | 72 | Notes 73 | ----- 74 | MS document ANSI keycodes: 75 | Pause = 0x1A 76 | Ctrl-Space = 0x00 77 | -------------------------------------------------------------------------------- /src/mos.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Matrix Brandy Basic VI Interpreter. 3 | ** Copyright (C) 2000-2014 David Daniels 4 | ** Copyright (C) 2018-2024 Michael McConnell, Jonathan Harston and contributors 5 | ** 6 | ** Brandy is free software; you can redistribute it and/or modify 7 | ** it under the terms of the GNU General Public License as published by 8 | ** the Free Software Foundation; either version 2, or (at your option) 9 | ** any later version. 10 | ** 11 | ** Brandy is distributed in the hope that it will be useful, 12 | ** but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | ** GNU General Public License for more details. 15 | ** 16 | ** You should have received a copy of the GNU General Public License 17 | ** along with Brandy; see the file COPYING. If not, write to 18 | ** the Free Software Foundation, 59 Temple Place - Suite 330, 19 | ** Boston, MA 02111-1307, USA. 20 | ** 21 | ** 22 | ** Functions that emulate the OS-specific parts of Basic live here 23 | */ 24 | 25 | #ifndef __mos_h 26 | #define __mos_h 27 | 28 | #include "common.h" 29 | 30 | extern void mos_oscli(char *, char *, FILE *); 31 | extern int32 mos_adval(int32); 32 | extern void mos_sound_on(void); 33 | extern void mos_sound_off(void); 34 | extern void mos_sound(int32, int32, int32, int32, int32); 35 | extern int64 mos_centiseconds(void); 36 | extern int32 mos_rdtime(void); 37 | extern void mos_wrtime(int32); 38 | extern void mos_rdrtc(char *); 39 | extern void mos_wrrtc(char *); 40 | extern void mos_call(int32, int32, int32 []); 41 | extern int32 mos_usr(int32); 42 | extern void mos_sys(size_t, sysparm[], size_t[], size_t*); 43 | extern size_t mos_getswinum(char *, int32, int32); 44 | extern void mos_setend(int32); 45 | extern void mos_waitdelay(int32); 46 | extern void mos_mouse_on(int32); 47 | extern void mos_mouse_off(void); 48 | extern void mos_mouse_to(int32, int32); 49 | extern void mos_mouse_step(int32, int32); 50 | extern void mos_mouse_colour(int32, int32, int32, int32); 51 | extern void mos_mouse_rectangle(int32, int32, int32, int32); 52 | extern void mos_mouse(size_t []); 53 | extern void mos_wrbeat(int32); 54 | extern int32 mos_rdbeat(void); 55 | extern int32 mos_rdbeats(void); 56 | extern void mos_wrtempo(int32); 57 | extern int32 mos_rdtempo(void); 58 | extern void mos_voice(int32, char *); 59 | extern void mos_voices(int32); 60 | extern void mos_stereo(int32, int32); 61 | extern boolean mos_init(void); 62 | extern void mos_final(void); 63 | 64 | extern byte *sysvar; 65 | #define sv_KeyboardBase 172 66 | #define sv_EscapeBreak 200 67 | #define sv_KBDDisabled 201 68 | #define sv_KBDStatus 202 69 | #define sv_TabChar 219 70 | #define sv_EscapeChar 220 71 | #define sv_KeyBase 221 72 | #define sv_EscapeAction 229 73 | #define sv_EscapeEffect 230 74 | #define sv_CursorKeys 237 75 | #define sv_KeypadBase 238 76 | #define sv_Country 240 77 | #define sv_KeyOptions 254 78 | 79 | #define sv_VideoVDU 250 80 | #define sv_VideoDisplay 251 81 | 82 | #define XBIT 0x20000 /* Mask for 'X' bit in SWI numbers */ 83 | 84 | #endif 85 | -------------------------------------------------------------------------------- /makefile.mingw-text: -------------------------------------------------------------------------------- 1 | # Makefile for brandy under Windows x86 / x64 with MinGW using Cygwin as the 2 | # toolchain 3 | 4 | # Find MinGW gcc 5 | compiler=$(shell which i686-w64-mingw32-gcc.exe 2>/dev/null) 6 | MINGWPATH=/usr/i686-w64-mingw32/sys-root/mingw 7 | ifeq ($(compiler),) 8 | compiler=$(shell which x86_64-w64-mingw32-gcc.exe 2>/dev/null) 9 | MINGWPATH=/usr/x86_64-w64-mingw32/sys-root/mingw 10 | ifeq ($(compiler),) 11 | $(error Unable to find MinGW gcc compiler) 12 | endif 13 | endif 14 | 15 | CC = $(compiler) 16 | LD = $(compiler) 17 | STRIP = strip 18 | ADDFLAGS = ${BRANDY_BUILD_FLAGS} 19 | 20 | include build/git.mk 21 | 22 | #CFLAGS = -g -DDEBUG -DCYGWINBUILD -DNO_SDL -DDEFAULT_IGNORE -D__USE_MINGW_ANSI_STDIO=1 -Wall $(GITFLAGS) $(ADDFLAGS) 23 | #CFLAGS = -g -DCYGWINBUILD -DDEFAULT_IGNORE -D__USE_MINGW_ANSI_STDIO=1 -Wall $(GITFLAGS) $(ADDFLAGS) 24 | CFLAGS = -O3 -DCYGWINBUILD -DNO_SDL -DDEFAULT_IGNORE -D__USE_MINGW_ANSI_STDIO=1 -Wall $(GITFLAGS) $(ADDFLAGS) 25 | 26 | LDFLAGS = 27 | 28 | LIBS = -lm -lws2_32 -mconsole $(MINGWPATH)/lib/libdxguid.a $(MINGWPATH)/lib/libwinmm.a $(MINGWPATH)/lib/libpthread.a $(MINGWPATH)/lib/libdl.a $(MINGWPATH)/lib/libpsapi.a 29 | 30 | SRCDIR = src 31 | 32 | OBJ = $(SRCDIR)/variables.o $(SRCDIR)/tokens.o \ 33 | $(SRCDIR)/strings.o $(SRCDIR)/statement.o $(SRCDIR)/stack.o \ 34 | $(SRCDIR)/miscprocs.o $(SRCDIR)/mainstate.o $(SRCDIR)/lvalue.o \ 35 | $(SRCDIR)/keyboard.o $(SRCDIR)/iostate.o $(SRCDIR)/heap.o \ 36 | $(SRCDIR)/functions.o $(SRCDIR)/fileio.o $(SRCDIR)/evaluate.o \ 37 | $(SRCDIR)/errors.o $(SRCDIR)/mos.o $(SRCDIR)/editor.o \ 38 | $(SRCDIR)/convert.o $(SRCDIR)/commands.o $(SRCDIR)/brandy.o \ 39 | $(SRCDIR)/assign.o $(SRCDIR)/net.o $(SRCDIR)/mos_sys.o 40 | 41 | TEXTONLYOBJ = $(SRCDIR)/textonly.o 42 | 43 | SIMPLETEXTOBJ = $(SRCDIR)/simpletext.o 44 | 45 | SRC = $(SRCDIR)/variables.c $(SRCDIR)/tokens.c \ 46 | $(SRCDIR)/strings.c $(SRCDIR)/statement.c $(SRCDIR)/stack.c \ 47 | $(SRCDIR)/miscprocs.c $(SRCDIR)/mainstate.c $(SRCDIR)/lvalue.c \ 48 | $(SRCDIR)/keyboard.c $(SRCDIR)/iostate.c $(SRCDIR)/heap.c \ 49 | $(SRCDIR)/functions.c $(SRCDIR)/fileio.c $(SRCDIR)/evaluate.c \ 50 | $(SRCDIR)/errors.c $(SRCDIR)/mos.c $(SRCDIR)/editor.c \ 51 | $(SRCDIR)/convert.c $(SRCDIR)/commands.c $(SRCDIR)/brandy.c \ 52 | $(SRCDIR)/assign.c $(SRCDIR)/net.c $(SRCDIR)/mos_sys.c 53 | 54 | TEXTONLYSRC = $(SRCDIR)/textonly.c 55 | 56 | SIMPLETEXTSRC = $(SRCDIR)/simpletext.c 57 | 58 | all: tbrandy sbrandy 59 | 60 | tbrandy: $(OBJ) $(TEXTONLYOBJ) 61 | $(LD) $(LDFLAGS) -o tbrandy $(OBJ) $(TEXTONLYOBJ) $(LIBS) 62 | 63 | sbrandy: $(OBJ) $(SIMPLETEXTOBJ) 64 | $(LD) $(LDFLAGS) -o sbrandy $(OBJ) $(SIMPLETEXTOBJ) $(LIBS) 65 | 66 | include build/depends.mk 67 | 68 | .c.o: 69 | $(CC) $(CFLAGS) $< -c -o $@ 70 | 71 | trecompile: 72 | $(CC) $(CFLAGS) $(SRC) $(TEXTONLYSRC) $(LIBS) -o tbrandy 73 | 74 | srecompile: 75 | $(CC) $(CFLAGS) $(SRC) $(SIMPLETEXTSRC) $(LIBS) -o sbrandy 76 | 77 | tnodebug: 78 | $(CC) $(CFLAGS2) $(SRC) $(TEXTONLYSRC) $(LIBS) -o tbrandy 79 | $(STRIP) tbrandy 80 | 81 | snodebug: 82 | $(CC) $(CFLAGS2) $(SRC) $(SIMPLETEXTSRC) $(LIBS) -o sbrandy 83 | $(STRIP) sbrandy 84 | 85 | tcheck: 86 | $(CC) $(CFLAGS) -Wall -O2 $(SRC) $(TEXTONLYSRC) $(LIBS) -o tbrandy 87 | 88 | scheck: 89 | $(CC) $(CFLAGS) -Wall -O2 $(SRC) $(SIMPLETEXTSRC) $(LIBS) -o sbrandy 90 | 91 | clean: 92 | rm -f $(SRCDIR)/*.o tbrandy sbrandy 93 | 94 | -------------------------------------------------------------------------------- /docs/Mode7.txt: -------------------------------------------------------------------------------- 1 | MODE 7 support in Brandy BASIC V/VI 2 | =================================== 3 | 4 | Under RISC OS, MODE 7 support is provided by RISC OS not Matrix Brandy, thus 5 | neither the OSWORD calls are not available nor the BBC-micro-like screen 6 | memory at &7C00, and on RISC OS versions before 5, the VDU calls are not 7 | supported. 8 | 9 | Mode 7 teletext charactes use 16x20 character cells, this allows for a 10 | decent rendering of mosaic graphics, especially separated graphics. 11 | 12 | Direct screen memory access is implemented, the address can be obtained by 13 | doing SYS "Brandy_GetVideoDriver" TO ,,,,addr% 14 | Usually this will return &7C00 but will return &FFFF7C00 if &7C00 is in 15 | BASIC workspace. It will always be a 32-bit address. 16 | 17 | Some RISC OS 5 extensions are also supported: 18 | (source: http://beebwiki.mdfs.net/VDU_23) 19 | 20 | VDU 23,18,2,flags,0,0,0,0,0,0 - Set Teletext reveal state 21 | bit 0 - if set, any concealed text will be displayed. If cleared, 22 | concealed text is concealed. 23 | Setting or clearing this will cause an immediate refresh of the display. 24 | 25 | VDU 23,18,3,enable,0,0,0,0,0,0 - Set Teletext black enable 26 | enable = 0: Control codes &80 and &90 do nothing (default) 27 | enable = 1: Control code &80 selects alphanumeric black, 28 | control code &90 selects graphics black. 29 | More strictly, this code toggle is an extended features toggle, which 30 | include Alpha Black (&80), Graphics Black (&90) and Alternative Character 31 | Set (&9B), and also corrects the Hold "bug" in the SAA5050 Teletext chip. 32 | 33 | VDU23,18,4,pri,alt,0,0,0,0,0 - Select Teletext character set 34 | The values are as per the SAA505x family of chips. This is extended in 35 | Matrix Brandy by ORing the value with 128 to substitute the solid block 36 | with the Euro symbol. pri is the Primary character set that is normally 37 | displayed, alt is the Alternative Character Set selected with &9B 38 | (if enabled using VDU23,18,3,1|) 39 | 40 | Two new OSWORD calls are available, one to read the character definition of 41 | a teletext character, another to change a character with a new definition. 42 | These OSWORD calls are specific to Matrix Brandy and Richard Russell's 43 | BBCSDL with whom these extensions were developed in parallel. 44 | 45 | OSWORD &8B (139) - Read a Teletext character definition. 46 | Requires a block size of 44. 47 | block%?0 = 4 48 | block%?1 = 44 49 | block%?2 = Character code 50 | block%?3 = Bank selecter, default 0 51 | block%?4..43 - Returned data 52 | 53 | OSWORD &8C (140) - Write a Teletext character definition to bank 0 54 | Requires a block size of 44 55 | block%?0 = 44 56 | block%?1 unused 57 | block%?2 = Character code 58 | block%?3 unused 59 | block%?4..43 = Character definition, in the same layout as &8B. 60 | 61 | OSBYTE 20 will reset the definition back to default along with the regular 62 | non-MODE7 font. 63 | OSBYTE 25 has been extended, if X=16 then reset teletext font only. 64 | 65 | The Alternative Character Set is implemented, it is toggled with teletext 66 | code ESCAPE (&9B), and defaults to the US-ASCII set as implemented on the 67 | SAA5055. The Alternative Character Set can be read and written to, use bank 68 | 0 and set the high bit on the character code. 69 | 70 | Note that the characters are shuffled, so the redefinitions are as follows: 71 | Redefine &23, change &60 and &A3. 72 | Redefine &5F, change &23 and &DF. 73 | Redefine &60, change &5F and &E0. 74 | This is also true for redefining &A3, &DF and &E0 in the alternative 75 | character set bank. 76 | -------------------------------------------------------------------------------- /src/graphsdl.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Matrix Brandy Basic VI Interpreter. 3 | ** Copyright (C) 2018-2024 Michael McConnell and contributors 4 | ** 5 | ** SDL additions by Colin Tuckley 6 | ** 7 | ** Brandy is free software; you can redistribute it and/or modify 8 | ** it under the terms of the GNU General Public License as published by 9 | ** the Free Software Foundation; either version 2, or (at your option) 10 | ** any later version. 11 | ** 12 | ** Brandy is distributed in the hope that it will be useful, 13 | ** but WITHOUT ANY WARRANTY; without even the implied warranty of 14 | ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15 | ** GNU General Public License for more details. 16 | ** 17 | ** You should have received a copy of the GNU General Public License 18 | ** along with Brandy; see the file COPYING. If not, write to 19 | ** the Free Software Foundation, 59 Temple Place - Suite 330, 20 | ** Boston, MA 02111-1307, USA. 21 | ** 22 | ** This file defines the exported functions which use the SDL library. 23 | */ 24 | #ifndef GRAPHSDL_INC 25 | #define GRAPHSDL_INC 26 | 27 | #ifndef MAXBANKS 28 | #ifdef BRANDY_MODE7ONLY 29 | #define MAXBANKS 1 30 | #else 31 | #define MAXBANKS 4 32 | #endif 33 | #endif /* defined MAXBANKS */ 34 | 35 | 36 | typedef struct { 37 | char *titlepointer; /* Not NULL to set title bar */ 38 | int32 mousecmd; /* Mouse toggle stuff */ 39 | int32 modechange; /* Is a mode change in flight? */ 40 | int32 x; /* X coordinate or parameter 1 */ 41 | int32 y; /* Y coordinate or parameter 2 */ 42 | int32 bailout; /* Set to 1 to exit the interpreter */ 43 | unsigned char crtc6845r10; /* CRTC Register 10, cursor control */ 44 | boolean mode7forcerefresh; /* Set to TRUE if we need a force refresh of MODE 7 */ 45 | boolean videothread; /* Set to 0 when video thread pass finished */ 46 | } threadmsg; 47 | 48 | extern void get_sdl_mouse(size_t values[]); 49 | extern void warp_sdlmouse(int32 x, int32 y); 50 | extern void sdl_mouse_onoff(int state); 51 | extern void fullscreenmode(int onoff); 52 | extern void setupnewmode(int32 mode, int32 xres, int32 yres, int32 cols, int32 mxscale, int32 myscale, int32 xeig, int32 yeig); 53 | extern void star_refresh(int flag); 54 | extern int get_refreshmode(void); 55 | extern int32 osbyte163_2(int x); 56 | extern void osbyte112(int x); 57 | extern void osbyte113(int x); 58 | extern int32 osbyte134_165(int32 a); 59 | extern int32 osbyte135(void); 60 | extern int32 osbyte163_242(int32 a); 61 | extern int32 osbyte250(void); 62 | extern int32 osbyte251(void); 63 | extern void reset_sysfont(int x); 64 | extern void hide_cursor(void); 65 | extern void osword09(int64 x); 66 | extern void osword0A(int64 x); 67 | extern void osword0B(int64 x); 68 | extern void osword0C(int64 x); 69 | extern void osword8B(int64 x); 70 | extern void osword8C(int64 x); 71 | extern void swi_os_setcolour(int32 r0, int32 r1); 72 | extern int32 os_readpalette(int32 colour, int32 mode); 73 | extern void sdl_screensave(char *fname); 74 | extern void sdl_screenload(char *fname); 75 | extern void swi_swap16palette(void); 76 | extern size_t readmodevariable(int32 scrmode, int32 var); 77 | extern void screencopy(int32 src, int32 dst); 78 | extern void refresh_location(uint32 offset); 79 | extern void add_mouseitem(int x, int y, int b, int64 c); 80 | extern void drain_mousebuffer(void); 81 | extern void set_mouseevent_expiry(uint32 expire); 82 | extern int videoupdatethread(void); 83 | 84 | extern Uint8 mousebuttonstate; 85 | extern mousequeue *mousebuffer; 86 | 87 | #endif 88 | -------------------------------------------------------------------------------- /CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.19.0) 2 | project(brandy LANGUAGES C) 3 | 4 | add_compile_options(-Wall) 5 | 6 | set(SRCDIR src) 7 | set(SRC ${SRCDIR}/variables.c ${SRCDIR}/tokens.c ${SRCDIR}/strings.c 8 | ${SRCDIR}/statement.c ${SRCDIR}/stack.c ${SRCDIR}/miscprocs.c 9 | ${SRCDIR}/mainstate.c ${SRCDIR}/lvalue.c ${SRCDIR}/keyboard.c 10 | ${SRCDIR}/iostate.c ${SRCDIR}/heap.c ${SRCDIR}/functions.c 11 | ${SRCDIR}/fileio.c ${SRCDIR}/evaluate.c ${SRCDIR}/errors.c 12 | ${SRCDIR}/mos.c ${SRCDIR}/editor.c ${SRCDIR}/convert.c 13 | ${SRCDIR}/commands.c ${SRCDIR}/brandy.c ${SRCDIR}/assign.c 14 | ${SRCDIR}/net.c ${SRCDIR}/mos_sys.c) 15 | 16 | add_executable(sbrandy ${SRC} ${SRCDIR}/simpletext.c) 17 | add_executable(tbrandy ${SRC} ${SRCDIR}/textonly.c) 18 | 19 | target_link_libraries(sbrandy m dl pthread) 20 | target_link_libraries(tbrandy m dl pthread) 21 | 22 | install(TARGETS sbrandy DESTINATION bin) 23 | install(TARGETS tbrandy DESTINATION bin) 24 | 25 | 26 | find_package(SDL 1.2) 27 | # We want to request a version before 2, but cmake does not support version 28 | # ranges for SDL. 29 | 30 | IF (SDL_FOUND) 31 | add_executable(brandy ${SRC} ${SRCDIR}/graphsdl.c ${SRCDIR}/soundsdl.c) 32 | 33 | target_link_libraries(brandy m dl pthread) 34 | target_include_directories(brandy PRIVATE ${SDL_INCLUDE_DIRS}) 35 | target_link_libraries(brandy m dl pthread ${SDL_LIBRARIES}) 36 | target_compile_definitions(brandy PRIVATE -DUSE_SDL) 37 | 38 | # libX11 may not be needed, eg., under Windows. 39 | find_package(X11) 40 | IF (X11_FOUND) 41 | target_link_libraries(brandy ${X11_LIBRARIES}) 42 | ENDIF() 43 | 44 | install(TARGETS brandy DESTINATION bin) 45 | ENDIF() 46 | 47 | IF (WIN32) 48 | add_compile_definitions(-DCYGWINBUILD) 49 | add_compile_definitions(-D__USE_MINGW_ANSI_STDIO) 50 | 51 | target_link_libraries(sbrandy ws2_32 psapi) 52 | target_link_libraries(tbrandy ws2_32 psapi) 53 | 54 | IF (SDL_FOUND) 55 | target_link_libraries(brandy ws2_32 psapi) 56 | ENDIF() 57 | 58 | ENDIF() 59 | 60 | IF (LINUX) 61 | target_link_libraries(sbrandy rt) 62 | target_link_libraries(tbrandy rt) 63 | 64 | IF (SDL_FOUND) 65 | target_link_libraries(brandy rt) 66 | ENDIF() 67 | ENDIF() 68 | 69 | # Inside "build-push-action" we have no .git. Rather than fighting, we put up 70 | # with it. 71 | IF (EXISTS .git) 72 | execute_process( 73 | COMMAND git rev-parse --short HEAD 74 | WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} 75 | OUTPUT_VARIABLE GIT_COMMIT 76 | OUTPUT_STRIP_TRAILING_WHITESPACE 77 | ) 78 | 79 | execute_process( 80 | COMMAND git rev-parse --abbrev-ref HEAD 81 | WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} 82 | OUTPUT_VARIABLE GIT_BRANCH 83 | OUTPUT_STRIP_TRAILING_WHITESPACE 84 | ) 85 | 86 | execute_process( 87 | COMMAND git log -1 --format=%cd 88 | WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} 89 | OUTPUT_VARIABLE GIT_DATE 90 | OUTPUT_STRIP_TRAILING_WHITESPACE 91 | ) 92 | 93 | add_compile_definitions(-DBRANDY_GITCOMMIT=\"${GIT_COMMIT}\" -DBRANDY_GITBRANCH=\"${GIT_BRANCH}\" -DBRANDY_GITDATE=\"${GIT_DATE}\") 94 | ENDIF() 95 | 96 | # Do not throw an error on missing features. 97 | add_compile_definitions(DEFAULT_IGNORE) 98 | 99 | enable_testing() 100 | 101 | # Shebang does not work on msys2, running "prove" directly does not work. 102 | IF (WIN32) 103 | find_program(PERL NAMES perl) 104 | find_program(PROVE NAMES prove) 105 | 106 | add_test(NAME Regressions COMMAND ${PERL} ${PROVE} --exec ${CMAKE_BINARY_DIR}/sbrandy -r t/) 107 | ELSE() 108 | add_test(NAME Regressions COMMAND prove --exec ${CMAKE_BINARY_DIR}/sbrandy -r t/) 109 | 110 | find_program(VALGRIND NAMES valgrind) 111 | IF (VALGRIND) 112 | add_test(NAME RegressionsValgrind COMMAND prove --exec "${VALGRIND} ${CMAKE_BINARY_DIR}/sbrandy" -r t/) 113 | ENDIF() 114 | ENDIF() 115 | -------------------------------------------------------------------------------- /examples/teklib: -------------------------------------------------------------------------------- 1 | REM NOTE: this library can only be used in an xterm session under 2 | REM Linux and NetBSD, or the Tektronix 3 | : 4 | REM This is a simple library that allows graphics to be plotted 5 | REM in a xterm window running under NetBSD or Linux using the 6 | REM Tektronics graphics terminal emulation that xterm offers. 7 | : 8 | REM The procedures and functions work in the same way that their 9 | REM Basic statement counterparts do. The Tektronics screen has 10 | REM a size of 1024 by 780 pixels. This library works in terms in 11 | REM RISC OS graphics units so the screen dimensions according to 12 | REM this code is 2048 graphics units by 1560. 13 | : 14 | : 15 | REM PROCmode initialises the variables used by the library and 16 | REM clears the graphics screen. It has to be called before any 17 | REM other procedure in this library 18 | : 19 | : 20 | : 21 | REM PROCtekvdu allows for a slowed-down Tek drawing, to simulate a 22 | REM serial-connected Tektronix terminal at approximately 9600bps 23 | REM Use a MODE >= 128 to run at full speed. 24 | : 25 | DEF PROCtekvdu(v%) 26 | IF tekfast% = 0 THEN SYS "Brandy_uSleep",890 27 | SYS 6,43,v% 28 | ENDPROC 29 | 30 | REM PROCclg clears the graphics screen 31 | : 32 | DEF PROCclg 33 | PROCtekvdu(27) 34 | PROCtekvdu(12) 35 | ENDPROC 36 | : 37 | DEF PROCmode(tekmode%) 38 | tek_gcx%=0 39 | tek_gcy%=0 40 | tek_originx%=0 41 | tek_originy%=0 42 | IF tekmode% > 127 THEN tekfast% = 1 ELSE tekfast% = 0 43 | PROCclg 44 | ENDPROC 45 | : 46 | : 47 | REM PROCorigin sets the coordinates of the graphics origin 48 | : 49 | DEF PROCorigin(X%, Y%) 50 | tek_originx%=X% 51 | tek_originy%=Y% 52 | ENDPROC 53 | : 54 | : 55 | REM PROCmove moves the graphics cursor to the coordinates given 56 | : 57 | DEF PROCmove(X%, Y%) 58 | tek_gcx%=(X%+tek_originx%) DIV 2 59 | tek_gcy%=(Y%+tek_originy%) DIV 2 60 | ENDPROC 61 | : 62 | : 63 | REM PROCdraw draws a line from the last graphics cursor position 64 | REM to the coordinates given, making them the new cursor position 65 | : 66 | DEF PROCdraw(X%, Y%) 67 | X%=(X%+tek_originx%) DIV 2 68 | Y%=(Y%+tek_originy%) DIV 2 69 | PROCtekvdu(29) 70 | PROCtekvdu((tek_gcy%>>5)+32) 71 | PROCtekvdu((tek_gcy% AND 31)+96) 72 | PROCtekvdu((tek_gcx%>>5)+32) 73 | PROCtekvdu((tek_gcx% AND 31)+64) 74 | PROCtekvdu((Y%>>5)+32) 75 | PROCtekvdu((Y% AND 31)+96) 76 | PROCtekvdu((X%>>5)+32) 77 | PROCtekvdu((X% AND 31)+64) 78 | PROCtekvdu(31) 79 | tek_gcx%=X% 80 | tek_gcy%=Y% 81 | ENDPROC 82 | : 83 | : 84 | REM PROCline draws a line from the coordinates (sx, sy) to (ex, ey). 85 | REM The graphics cursor position is set to (ex, ey) 86 | : 87 | DEF PROCline(sx%, sy%, ex%, ey%) 88 | sx%=(sx%+tek_originx%) DIV 2 89 | sy%=(sy%+tek_originy%) DIV 2 90 | ex%=(ex%+tek_originx%) DIV 2 91 | ey%=(ey%+tek_originy%) DIV 2 92 | PROCtekvdu(29) 93 | PROCtekvdu((sy%>>5)+32) 94 | PROCtekvdu((sy% AND 31)+96) 95 | PROCtekvdu((sx%>>5)+32) 96 | PROCtekvdu((sx% AND 31)+64) 97 | PROCtekvdu((ey%>>5)+32) 98 | PROCtekvdu((ey% AND 31)+96) 99 | PROCtekvdu((ex%>>5)+32) 100 | PROCtekvdu((ex% AND 31)+64) 101 | PROCtekvdu(31) 102 | tek_gcx%=ex% 103 | tek_gcy%=ey% 104 | ENDPROC 105 | : 106 | : 107 | REM PROCpoint plots a single point 108 | : 109 | DEF PROCpoint(X%, Y%) 110 | X%=(X%+tek_originx%) DIV 2 111 | Y%=(Y%+tek_originy%) DIV 2 112 | PROCtekvdu(29) 113 | PROCtekvdu((Y%>>5)+32) 114 | PROCtekvdu((Y% AND 31)+96) 115 | PROCtekvdu((X%>>5)+32) 116 | PROCtekvdu((X% AND 31)+64) 117 | PROCtekvdu((Y%>>5)+32) 118 | PROCtekvdu((Y% AND 31)+96) 119 | PROCtekvdu((X%>>5)+32) 120 | PROCtekvdu((X% AND 31)+64) 121 | PROCtekvdu(31) 122 | tek_gcx%=X% 123 | tek_gcy%=Y% 124 | ENDPROC 125 | : 126 | DEFPROCtekinit 127 | tekfast%=0 128 | PROCtekvdu(27) 129 | PROCtekvdu(91) 130 | PROCtekvdu(63) 131 | PROCtekvdu(51) 132 | PROCtekvdu(56) 133 | PROCtekvdu(104) 134 | ENDPROC 135 | : 136 | DEFPROCtekexit 137 | PROCtekvdu(27) 138 | PROCtekvdu(3) 139 | ENDPROC 140 | -------------------------------------------------------------------------------- /src/common.h: -------------------------------------------------------------------------------- 1 | /* 2 | ** This file is part of the Matrix Brandy Basic VI Interpreter. 3 | ** Copyright (C) 2000-2014 David Daniels 4 | ** Copyright (C) 2018-2024 Michael McConnell and contributors 5 | ** 6 | ** Brandy is free software; you can redistribute it and/or modify 7 | ** it under the terms of the GNU General Public License as published by 8 | ** the Free Software Foundation; either version 2, or (at your option) 9 | ** any later version. 10 | ** 11 | ** Brandy is distributed in the hope that it will be useful, 12 | ** but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | ** GNU General Public License for more details. 15 | ** 16 | ** You should have received a copy of the GNU General Public License 17 | ** along with Brandy; see the file COPYING. If not, write to 18 | ** the Free Software Foundation, 59 Temple Place - Suite 330, 19 | ** Boston, MA 02111-1307, USA. 20 | ** 21 | ** 22 | ** Types and constants used throughout the interpreter 23 | */ 24 | 25 | #ifndef __common_h 26 | #define __common_h 27 | 28 | #define FALSE 0 29 | #define TRUE 1 30 | #define NIL 0 31 | #ifndef NUL 32 | #define NUL 0 33 | #endif 34 | #ifndef LF 35 | #define LF 10 36 | #endif 37 | #ifndef ESC 38 | #define ESC 27 39 | #endif 40 | 41 | #define MAXINTVAL 2147483647ll 42 | #define MININTVAL -2147483648ll 43 | #define MAXINT64VAL 0x7FFFFFFFFFFFFFFFll 44 | #define MAXINT64FLT 9223372036854775807.0L 45 | #define MININT64VAL 0x8000000000000000ll 46 | #define MININT64FLT -9223372036854775808.0L 47 | #define SMALLCONST 256 48 | #define MAXFLOATVAL 1.7976931348623157E+308 49 | #define TINYFLOATVAL 2.2250738585072014E-308 50 | #define MAXEXPONENT 308 51 | 52 | #ifndef PI 53 | #define PI 3.141592653589793238462643383279502884L 54 | #endif 55 | 56 | #define MAXSTATELEN 1024 /* Maximum length of a tokenised line of Basic */ 57 | #define MINSTATELEN 7 /* Minimum legal length of a tokenised line */ 58 | #define MAXLINENO 65279 /* Highest line number allowed */ 59 | #define ENDLINENO 0xFF00 /* Line number value used to mark end of program */ 60 | #define INTSIZE 4 /* Size of a 32-bit integer in bytes */ 61 | #define INT64SIZE 8 /* Size of a 64-bit integer in bytes */ 62 | #define SMALLSIZE 1 /* Size of a small integer */ 63 | #define FLOATSIZE 8 /* Size of a floating point value */ 64 | #define STRINGSIZE 8 /* Size of a string descriptor block */ 65 | #define LOFFSIZE 4 /* Size of a long offset embedded in the code */ 66 | #define OFFSIZE 2 /* Size of a short offset embedded in the code */ 67 | #define LINESIZE 2 /* Size of a line number */ 68 | #define LENGTHSIZE 2 /* Size of the line length */ 69 | #define SIZESIZE 2 /* Size of string size embedded in the code */ 70 | #define MAXDIMS 10 /* Maximum number of array dimensions allowed */ 71 | #define MAXNAMELEN 256 /* Size of buffers used to hold variable names */ 72 | 73 | #define asc_CR 0xD 74 | #define asc_LF 0xA 75 | #define asc_TAB '\t' 76 | #define asc_NUL '\0' 77 | #define asc_ESC 0x1B 78 | #define asc_VBAR 0x7C 79 | 80 | #define BYTEMASK 0xFF 81 | #define BYTESHIFT 8 82 | 83 | typedef unsigned char byte; 84 | typedef unsigned char boolean; 85 | 86 | /* These macros hide type casts */ 87 | 88 | #define CAST(x,y) ((y)(x)) 89 | /* TOINT macro redefined as fuction to allow range check, in miscprocs */ 90 | #define TOFLOAT(x) ((float64)(x)) 91 | #define TOSTRING(x) ((char *)(x)) 92 | #define TOINTADDR(x) ((int32 *)(x)) 93 | 94 | /* These exist in the RISC OS UnixLib but are missing from the headers */ 95 | #ifdef TARGET_RISCOS 96 | extern float80 powl(long double x, long double y); 97 | extern float80 fabsl(long double x); 98 | #endif 99 | 100 | #endif 101 | -------------------------------------------------------------------------------- /examples/SAA505Xlib: -------------------------------------------------------------------------------- 1 | 10REM > SAA505Xlib 2 | 20REM A library for switching the MODE 7 language settings as per the 3 | 30REM SAA505X family of Teletext character generators from Mullard. 4 | 40REM Currently the supported codes are: 0 / 5050: English (default), 5 | 50REM 1 / 5051: German, 2 / 5052: Swedish, 3 / 5053: Italian, 6 | 60REM 4 / 5054: Belgian, 5 / 5055: US ASCII, 6 / 5056: Hebrew and 7 | 70REM 7 / 5057: Cyrillic 8 | 80DEFPROCsaa505xlibset(code%, alt%) 9 | 90LOCAL loop%, j% 10 | 100j%=0: IF alt% THEN j%=128 11 | 110SYS "OS_Byte",42,1 12 | 120PROCsaa505xreset(alt%,0) 13 | 130CASE code% OF 14 | 140WHEN 0,5050: REM English, default 15 | 150WHEN 1,5051: REM German 16 | 160 PROCsaa505xr(&23,j%+&23,1): PROCsaa505xr(&A7,j%+&40,1): PROCsaa505xr(&C4,j%+&5B,1): PROCsaa505xr(&D6,j%+&5C,1) 17 | 170 PROCsaa505xr(&DC,j%+&5D,1): PROCsaa505xr(&5E,j%+&5E,1): PROCsaa505xr(&5F,j%+&5F,1): PROCsaa505xr(&B0,j%+&60,1) 18 | 180 PROCsaa505xr(&E4,j%+&7B,1): PROCsaa505xr(&F6,j%+&7C,1): PROCsaa505xr(&FC,j%+&7D,1): PROCsaa505xr(&DF,j%+&7E,1) 19 | 190WHEN 2,5052: REM Swedish 20 | 200 PROCsaa505xr(&23,j%+&23,1): PROCsaa505xr(&A4,j%+&24,1): PROCsaa505xr(&C9,j%+&40,1): PROCsaa505xr(&C4,j%+&5B,1) 21 | 210 PROCsaa505xr(&D6,j%+&5C,1): PROCsaa505xr(&C5,j%+&5D,1): PROCsaa505xr(&DC,j%+&5E,1): PROCsaa505xr(&5F,j%+&5F,1) 22 | 220 PROCsaa505xr(&E9,j%+&60,1): PROCsaa505xr(&E4,j%+&7B,1): PROCsaa505xr(&F6,j%+&7C,1): PROCsaa505xr(&E5,j%+&7D,1) 23 | 230 PROCsaa505xr(&FC,j%+&7E,1) 24 | 240WHEN 3,5053: REM Italian 25 | 250 PROCsaa505xr(&E9,j%+&40,1): PROCsaa505xr(&B0,j%+&5B,1): PROCsaa505xr(&E7,j%+&5C,1): PROCsaa505xr(&D9,j%+&60,1) 26 | 260 PROCsaa505xr(&E0,j%+&7B,1): PROCsaa505xr(&D2,j%+&7C,1): PROCsaa505xr(&E8,j%+&7D,1): PROCsaa505xr(&EC,j%+&7E,1) 27 | 270WHEN 4,5054: REM Belgian/French 28 | 280 PROCsaa505xr(&E9,j%+&23,1): PROCsaa505xr(&EF,j%+&24,1): PROCsaa505xr(&E0,j%+&40,1): PROCsaa505xr(&EB,j%+&5B,1) 29 | 290 PROCsaa505xr(&EA,j%+&5C,1): PROCsaa505xr(&D9,j%+&5D,1): PROCsaa505xr(&EE,j%+&5E,1): PROCsaa505xr(&E8,j%+&60,1) 30 | 300 PROCsaa505xr(&E2,j%+&7B,1): PROCsaa505xr(&F4,j%+&7C,1): PROCsaa505xr(&FB,j%+&7D,1): PROCsaa505xr(&E7,j%+&7E,1) 31 | 310WHEN 5,5055: REM US-ASCII 32 | 320 FOR loop%=&5B TO &60:PROCsaa505xr(loop%, loop%+j%,1):NEXT 33 | 330 PROCsaa505xr(&23,j%+&23,1): PROCsaa505xr(&7B,j%+&7B,1): PROCsaa505xr(&7C,j%+&7C,1): PROCsaa505xr(&7D,j%+&7D,1): PROCsaa505xr(&7E,j%+&7E,1) 34 | 340WHEN 6,5056: REM Hebrew 35 | 350 FOR loop%=0 TO 27:PROCsaa505xr(loop%,j%+loop%+&60,1):NEXT 36 | 360WHEN 7,5057: REM Cyrillic 37 | 370 FOR loop%=0 TO &3E:PROCsaa505xr(loop%,j%+loop%+&40,2):NEXT 38 | 380 PROCsaa505xr(&23,j%+&23,1): PROCsaa505xr(&3F,j%+&26,2) 39 | 390ENDCASE 40 | 400SYS "OS_Byte",42,2 41 | 410ENDPROC 42 | 420: 43 | 430DEFPROCsaa505xmapeuro(alt%) 44 | 440PROCsaa505xr(&80,&7F+(&80*alt%),1) 45 | 450ENDPROC 46 | 460: 47 | 470DEFPROCsaa505xreset(alt%, f%): REM Reset a font table to SAA5050 layout 48 | 480LOCAL loop%, j% 49 | 490j%=0:IF alt% THEN j%=128 50 | 500IF f% THEN SYS"OS_Byte",42,1 51 | 510FOR loop%=32TO126:PROCsaa505xr(loop%,loop%+j%,1):NEXT 52 | 520PROCsaa505xr(&A3,j%+&23,1): PROCsaa505xr(&8F,j%+&5B,1): PROCsaa505xr(&BD,j%+&5C,1): PROCsaa505xr(&90,j%+&5D,1) 53 | 530PROCsaa505xr(&8D,j%+&5E,1): PROCsaa505xr(&23,j%+&5F,1) :PROCsaa505xr(&96,j%+&60,1): PROCsaa505xr(&BC,j%+&7B,1) 54 | 530PROCsaa505xr(&9D,j%+&7C,1): PROCsaa505xr(&BE,j%+&7D,1): PROCsaa505xr(&F7,j%+&7E,1): PROCsaa505xr(&81,j%+&7F,1) 55 | 540IF f% THEN SYS"OS_Byte",42,2 56 | 550ENDPROC 57 | 560: 58 | 570DEFPROCsaa505xr(chi%, cho%, bank%) 59 | 580LOCAL blk%% 60 | 590DIM HIMEM blk%% 64 61 | 600blk%%?0 = 4 62 | 610blk%%?1 = 44 63 | 620blk%%?2 = chi% 64 | 630blk%%?3 = bank% 65 | 640SYS "OS_Word",&8B,blk%% 66 | 650blk%%?0 = 44 67 | 660blk%%?1 = 0 68 | 670blk%%?2 = cho% 69 | 680blk%%?3 = 0 70 | 690SYS "OS_Word",&8C,blk%% 71 | 700DIM HIMEM blk%% -1 72 | 710ENDPROC 73 | -------------------------------------------------------------------------------- /examples/Mode7/M7terminal: -------------------------------------------------------------------------------- 1 | 10REM>M7terminal 2 | 20ON ERROR PRINT REPORT$: M%=INKEY(500): END 3 | 30SYS"OS_Byte",229,1: REM Disable ESCAPE 4 | 40*WinTitle Matrix Network MODE 7 Terminal 5 | 50MODE 7 6 | 60C%=0:D%=0:K%=0: DIM xmbuf%% 132, filebuf%% 32768 7 | 70conn$=FNaddr 8 | 80PRINT "Connecting..." 9 | 90H%=OPENUP(conn$) 10 | 100IF H%=0 THEN PRINT "Connection failed": M%=INKEY(500): END 11 | 110CLS 12 | 120REPEAT 13 | 130C%=BGET#H% 14 | 140IF C%=-2 THEN PRINT'"Connection terminated, press any key": M%=GET: END 15 | 150IF C%<>-1 VDU C% 16 | 160UNTIL C%=-1 17 | 170K%=INKEY(5) 18 | 180IF K%>=32 AND K%<128 BPUT#H%,K% 19 | 190IF K%=8 OR K%=11 OR K%=13 OR K%=17 OR K%=19 THEN BPUT#H%,K% 20 | 200IF K%=4 THEN PROCclose 21 | 210IF K%=18 PROCrecv_xmodem 22 | 220GOTO 120 23 | 230DEFPROCclose 24 | 240IF H%=0 THEN PRINT:GOTO 290 25 | 250BPUT#H%,13:BPUT#H%,13 26 | 260FOR N%=1TO40:BPUT#H%,ASC("Q"):NEXT 27 | 270CLOSE#H% 28 | 280PRINT'"Connection closed": WAIT 300 29 | 290END 30 | 300ENDPROC 31 | 310: 32 | 320DEFFNaddr 33 | 330OFF 34 | 340VDU32,157,132,141:PRINT" Matrix Network MODE 7 Terminal ";:VDU156:PRINT 35 | 350VDU32,157,132,141:PRINT" Matrix Network MODE 7 Terminal ";:VDU156:PRINT 36 | 360VDU132,157,135:PRINT" V0.000002 (09 Feb 2024) ";:VDU156:PRINT' 37 | 370PRINT" This is a client for";CHR$134;"MODE 7";CHR$(135)"bulletin" 38 | 380PRINT" board systems. This is";CHR$129;"not";CHR$135;"suitable" 39 | 390PRINT" for Viewdata servers. To connect to" 40 | 400PRINT" those please use the";CHR$131;"Telstar";CHR$135;"client"'" instead."' 41 | 410VDU131:PRINT "1: BeeBS" 42 | 420PRINT 43 | 430VDU130:PRINT "9: Enter address":PRINT 44 | 440VDU129:PRINT "0: Exit terminal"' 45 | 450VDU130:PRINT "Within the session, press";CHR$133;"CTRL-R";CHR$130;"to" 46 | 460VDU130:PRINT "start an Xmodem (CP/M) file download." 47 | 470K%=GET 48 | 480IF K%=49 addr$="beebs.ddns.net:6502":GOTO520 49 | 490IF K%=57 ON: INPUTLINE"Address>"addr$:GOTO520 50 | 500IF K%=48 OR K%=27 THEN ON:CLS:END 51 | 510GOTO470 52 | 520REM Jump out 53 | 530CLS:ON 54 | 540="ip0:"+addr$ 55 | 550: 56 | 560DEFPROCrecv_xmodem 57 | 570LOCAL d%,blks% 58 | 580blks%=0:break%=0 59 | 590BPUT#H%,21: REM NAK to initiate the transfer 60 | 600d%=FNgetchr 61 | 610IF d%=4 THEN PRINT "Received EOT": GOTO 700: REM EOT received 62 | 620IF d%<>1 THEN PRINT "Got unexpected byte &";~d%: GOTO 590: REM Expected SOH 63 | 630REM Received SOH, let's get the packet, 131 bytes. 64 | 640PRINT "Reading block... "; 65 | 650FOR p%=0 TO 130:xmbuf%%?p%=FNgetchr: IF INKEY(-113) break%=TRUE 66 | 660NEXT 67 | 670IFbreak% GOTO 810 68 | 680IF FNchksum THEN blks%=?xmbuf%%: PROCstore: BPUT#H%,6 ELSE BPUT#H%,21 69 | 690GOTO 600 70 | 700REM EOT received, do end of file transfer handling 71 | 710BPUT#H%,21: REM Send a NAK 72 | 720d%=FNgetchr 73 | 730IF d%<>4 THEN GOTO 830 74 | 740BPUT#H%,6 75 | 750PRINT "File completed in ";blks%;" 128-byte blocks." 76 | 760INPUTLINE "Filename to save as >"fn$ 77 | 770fh%=OPENOUT(fn$) 78 | 780FOR p%=0 TO (128*blks%)-1: BPUT#fh%, filebuf%%?p%: NEXT 79 | 790CLOSE#fh% 80 | 800GOTO850 81 | 810REM Break out, abort transfer 82 | 820PRINT"Escape - "; 83 | 830PRINT"Breaking out, aborting" 84 | 840BPUT#H%,24: REM CAN 85 | 850ENDPROC 86 | 860: 87 | 870DEFFNgetchr 88 | 880LOCAL c% 89 | 890REPEAT c%=BGET#H%: UNTIL c%<>-1 90 | 900IF c%=-2 THEN PRINT'"Connection terminated, transfer failed": END 91 | 910=c% 92 | 920: 93 | 930DEFFNchksum: REM Returns TRUE if checksum passes 94 | 940IF (?xmbuf%% + xmbuf%%?1) <> 255 THEN PRINT "";?xmbuf%%;" header FAILED":=FALSE 95 | 950sum%=0 96 | 960FOR p%=2 TO 129:sum%+=xmbuf%%?p%:NEXT 97 | 970sum% AND=&FF 98 | 980PRINT "";?xmbuf%%; 99 | 990IF sum% = xmbuf%%?130 THEN PRINT " OK";:VDU13:=TRUE ELSE PRINT " FAILED": =FALSE 100 | 1000: 101 | 1010DEFPROCstore 102 | 1020LOCAL b% 103 | 1030b%=(?xmbuf%%)-1 104 | 1040FOR p%=0 TO 127:filebuf%%?((128*b%)+p%)=xmbuf%%?(p%+2):NEXT 105 | 1050ENDPROC 106 | -------------------------------------------------------------------------------- /.github/workflows/actions.yml: -------------------------------------------------------------------------------- 1 | name: Build and run tests 2 | 3 | on: [push, pull_request] 4 | 5 | jobs: 6 | cmake: 7 | runs-on: ${{ matrix.os }} 8 | strategy: 9 | matrix: 10 | os: ['ubuntu-24.04', 'ubuntu-22.04'] 11 | cc: [ 'gcc', 'clang' ] 12 | name: Compile via CMakeLists.txt on ${{ matrix.os }} using ${{ matrix.cc }} 13 | env: 14 | CC: ${{ matrix.cc }} 15 | CXX: ${{ matrix.cc }} 16 | CFLAGS: "-Wextra" 17 | steps: 18 | - uses: actions/checkout@v2 19 | - run: sudo apt-get update && sudo apt-get install libsdl1.2-dev valgrind 20 | - run: cmake . 21 | - run: cmake --build . 22 | - run: ctest --rerun-failed --output-on-failure 23 | make: 24 | runs-on: ${{ matrix.os }} 25 | strategy: 26 | matrix: 27 | os: ['ubuntu-24.04', 'ubuntu-22.04'] 28 | makefile: ['makefile'] 29 | name: Compile via ${{ matrix.os }} on ${{ matrix.os }} 30 | env: 31 | BRANDY_BUILD_FLAGS: "-Wextra" 32 | steps: 33 | - uses: actions/checkout@v2 34 | - run: sudo apt-get update && sudo apt-get install libsdl1.2-dev 35 | - run: make -f ${{ matrix.makefile }} 36 | make_text: 37 | runs-on: ${{ matrix.os }} 38 | strategy: 39 | matrix: 40 | os: ['ubuntu-24.04', 'ubuntu-22.04'] 41 | makefile: ['makefile.text'] 42 | name: Compile via ${{ matrix.makefile }} Makefile on ${{ matrix.os }} 43 | env: 44 | BRANDY_BUILD_FLAGS: "-Wextra" 45 | steps: 46 | - uses: actions/checkout@v2 47 | - run: make -f ${{ matrix.makefile }} 48 | - run: make -f ${{ matrix.makefile }} test 49 | cmake_macos: 50 | runs-on: ${{ matrix.os }} 51 | strategy: 52 | matrix: 53 | os: ['macos-latest', 'macos-14'] 54 | name: Compile via cmake on ${{ matrix.os }} 55 | env: 56 | CFLAGS: "-Wextra" 57 | steps: 58 | - uses: actions/checkout@v2 59 | - run: cmake . 60 | - run: cmake --build . 61 | - run: ctest --rerun-failed --output-on-failure 62 | 63 | cmake_windows: 64 | runs-on: ${{ matrix.runs-on }} 65 | strategy: 66 | fail-fast: false 67 | matrix: 68 | include: 69 | - { icon: '🟦', sys: mingw64, runs-on: 'windows-latest' } 70 | - { icon: '🟨', sys: ucrt64, runs-on: 'windows-latest' } 71 | - { icon: '🟧', sys: clang64, runs-on: 'windows-latest' } 72 | # clangarm64 currently fails: https://github.com/llvm/llvm-project/issues/136358 73 | # - { icon: '🟩', sys: clangarm64, runs-on: 'windows-11-arm' } 74 | name: Compile via cmake on ${{ matrix.sys }} 75 | env: 76 | CFLAGS: "-Wextra" 77 | defaults: 78 | run: 79 | shell: msys2 {0} 80 | steps: 81 | - uses: actions/checkout@v2 82 | - name: '${{ matrix.icon }} Setup MSYS2' 83 | uses: msys2/setup-msys2@v2 84 | with: 85 | msystem: ${{matrix.sys}} 86 | update: true 87 | install: >- 88 | git 89 | make 90 | pacboy: >- 91 | toolchain:p 92 | cmake:p 93 | ninja:p 94 | dlfcn:p 95 | sdl12-compat:p 96 | perl:p 97 | - run: cmake . 98 | - run: cmake --build . 99 | - run: ctest --rerun-failed --output-on-failure 100 | 101 | docker-build-and-test: 102 | runs-on: ubuntu-latest 103 | strategy: 104 | fail-fast: false 105 | matrix: 106 | platform: 107 | - linux/amd64 108 | - linux/arm64 109 | - linux/386 110 | - linux/arm/v6 111 | - linux/arm/v7 112 | - linux/ppc64le 113 | - linux/s390x 114 | steps: 115 | - name: Docker meta 116 | id: meta 117 | uses: docker/metadata-action@v5 118 | with: 119 | images: ${{ env.REGISTRY_IMAGE }} 120 | 121 | - name: Set up QEMU 122 | uses: docker/setup-qemu-action@v3 123 | 124 | - name: Set up Docker Buildx 125 | uses: docker/setup-buildx-action@v3 126 | 127 | - name: Build and push by digest 128 | id: build 129 | uses: docker/build-push-action@v6 130 | with: 131 | platforms: ${{ matrix.platform }} 132 | file: Dockerfile.sbrandy 133 | -------------------------------------------------------------------------------- /examples/hex: -------------------------------------------------------------------------------- 1 | REM Work out solutions to the "hex" problem. The idea here 2 | REM is to find all the solutions to a magic square where the 3 | REM numbers 1 to 19 have to be arranged in a hex pattern 4 | REM so that all the straight lines add up to 38 thus: 5 | REM 6 | REM xx xx xx 7 | REM xx xx xx xx 8 | REM xx xx xx xx xx 9 | REM xx xx xx xx 10 | REM xx xx xx 11 | : 12 | threesize%=200 13 | : 14 | DIM jval%(threesize%), kval%(threesize%), nextpos%(threesize%) 15 | DIM xlistpos%(19), used%(19), ring%(19), checks%(6,3), does%(6) 16 | : 17 | T=TIME 18 | checks%(1,1)=8: checks%(1,2)=12: checks%(1,3)=18 19 | checks%(2,1)=2: checks%(2,2)=10: checks%(2,3)=18 20 | checks%(3,1)=4: checks%(3,2)=12: checks%(3,3)=13 21 | checks%(4,1)=6: checks%(4,2)=10: checks%(4,3)=17 22 | checks%(5,1)=2: checks%(5,2)=6: checks%(5,3)=14 23 | checks%(6,1)=4: checks%(6,2)=8: checks%(6,3)=16 24 | does%(1)=17 25 | does%(2)=13 26 | does%(3)=14 27 | does%(4)=16 28 | does%(5)=15 29 | does%(6)=15 30 | nosol%=0 31 | num%=0 32 | FOR I%=1 TO 19 33 | used%(I%)=FALSE 34 | xlistpos%(I%)=0 35 | NEXT 36 | : 37 | FOR I%=3 TO 19 38 | FOR J%=1 TO 19 39 | IF I%<>J% THEN 40 | FOR K%=3 TO 19 41 | IF (K%<>J%) AND (K%<>I%) AND (I%+J%+K%=38) THEN 42 | num%+=1 43 | next%=num% 44 | jval%(next%)=J% 45 | kval%(next%)=K% 46 | nextpos%(next%)=xlistpos%(I%) 47 | xlistpos%(I%)=next% 48 | ENDIF 49 | NEXT 50 | ENDIF 51 | NEXT 52 | NEXT 53 | PRINT FNdec(num%,3);" number groups generated" 54 | : 55 | FOR I%=3 TO 19 56 | P%=xlistpos%(I%) 57 | used%(I%)=TRUE 58 | WHILE P%<>0 59 | J%=jval%(P%) 60 | K%=kval%(P%) 61 | used%(J%)=TRUE 62 | used%(K%)=TRUE 63 | ring%(1)=I% 64 | ring%(2)=J% 65 | curr%=2 66 | PROCfillin(K%) 67 | used%(J%)=FALSE 68 | used%(K%)=FALSE 69 | P%=nextpos%(P%) 70 | ENDWHILE 71 | used%(I%)=FALSE 72 | NEXT 73 | PRINT"There are";FNdec(nosol%,3);" solutions" 74 | PRINT"Time taken: ";(TIME-T)/100;" seconds" 75 | END 76 | : 77 | : 78 | DEF FNdec(X%,W%)=RIGHT$(" "+STR$X%,W%) 79 | : 80 | : 81 | DEF PROCblockin(target%) 82 | LOCAL total%, poss%, I% 83 | IF target%>5 THEN 84 | IF (38-ring%(4)-ring%(8)-ring%(16))=ring%(15) THEN 85 | poss%=1 86 | WHILE used%(poss%) 87 | poss%+=1 88 | ENDWHILE 89 | IF (38-ring%(11)-ring%(18)-ring%(15)-ring%(5))=poss% THEN 90 | ring%(19)=poss% 91 | nosol%+=1 92 | PRINT"Solution no.";FNdec(nosol%,3)'' 93 | PRINT" ";FNdec(ring%(1),2);FNdec(ring%(2),4);FNdec(ring%(3),4) 94 | PRINT" ";FNdec(ring%(12),2);FNdec(ring%(13),4);FNdec(ring%(14),4);FNdec(ring%(4),4) 95 | PRINT" ";FNdec(ring%(11),2);FNdec(ring%(18),4);FNdec(ring%(19),4);FNdec(ring%(15),4);FNdec(ring%(5),4) 96 | PRINT" ";FNdec(ring%(10),2);FNdec(ring%(17),4);FNdec(ring%(16),4);FNdec(ring%(6),4) 97 | PRINT" ";FNdec(ring%(9),2);FNdec(ring%(8),4);FNdec(ring%(7),4)'' 98 | ENDIF 99 | ENDIF 100 | ELSE 101 | total%=38 102 | FOR I%=1 TO 3 103 | total%=total%-ring%(checks%(target%,I%)) 104 | NEXT 105 | IF (total%>0) AND (total%<20) THEN 106 | IF NOT used%(total%) THEN 107 | used%(total%)=TRUE 108 | ring%(does%(target%))=total% 109 | PROCblockin(target%+1) 110 | used%(total%)=FALSE 111 | ENDIF 112 | ENDIF 113 | ENDIF 114 | ENDPROC 115 | : 116 | DEF PROCfillin(pi%) 117 | LOCAL I%, pj%, pk%, pos1%, ptr% 118 | ptr%=xlistpos%(pi%) 119 | WHILE ptr%<>0 120 | pj%=jval%(ptr%) 121 | pk%=kval%(ptr%) 122 | IF NOT used%(pj%) AND NOT used%(pk%) THEN 123 | used%(pj%)=TRUE 124 | used%(pk%)=TRUE 125 | ring%(curr%+curr%-1)=pi% 126 | ring%(curr%+curr%)=pj% 127 | curr%+=1 128 | IF curr%<7 THEN PROCfillin(pk%) 129 | used%(pk%)=FALSE 130 | used%(pj%)=FALSE 131 | curr%-=1 132 | ELSE 133 | IF curr%=6 THEN 134 | IF NOT used%(pj%) AND pk%=ring%(1) THEN 135 | used%(pj%)=TRUE 136 | ring%(11)=pi% 137 | ring%(12)=pj% 138 | FOR I%=1 TO 19 139 | IF NOT used%(I%) THEN 140 | ring%(18)=I% 141 | used%(I%)=TRUE 142 | PROCblockin(1) 143 | used%(I%)=FALSE 144 | ENDIF 145 | NEXT 146 | used%(pj%)=FALSE 147 | ENDIF 148 | ENDIF 149 | ENDIF 150 | ptr%=nextpos%(ptr%) 151 | ENDWHILE 152 | ENDPROC 153 | -------------------------------------------------------------------------------- /examples/platformcheck: -------------------------------------------------------------------------------- 1 | 10REM > platformcheck 2 | 20i%=INKEY(-256) AND &FF 3 | 30IF i%=&4D THEN PROCmatrix: END 4 | 40IF i%=&53 OR i%=&73 OR i%=&57 THEN PROCrtrbasic:END 5 | 50IF (i% AND &F0)=&A0 THEN SYS "OS_Byte",0,1 TO ,mactype% ELSE A%=0:X%=1:Y%=0:mactype%=(USR&FFF4 AND &FF00) DIV 256 6 | 60PRINT "Running on BBC BASIC on INKEY-type ";FNlegacy(i%);" (&";~i%;"), OSBYTE-0 type ";FNmactype 7 | 70END 8 | 80DEFPROCrtrbasic 9 | 90os%=@platform% AND &FF 10 | 100b64%=os% AND &40: os% = os% AND &BF 11 | 110IF i% = &57 THEN PRINT "Running on BBC BASIC for Windows": ENDPROC 12 | 120IF i% = &73 THEN PRINT "Running on BBC BASIC for SDL on ";FNbbcsdlos;" on ";FNbitness;" ARM hardware":ENDPROC 13 | 130PRINT "BBC BASIC for SDL on ";FNbbsdlos;" on ";FNbitness;" Intel hardware" 14 | 140ENDPROC 15 | 150DEF FNbitness 16 | 160IF b64% THEN ="64-bit" ELSE ="32-bit" 17 | 170DEF FNbbcsdlos 18 | 180CASE os% OF 19 | 190WHEN 0: ="Microsoft Windows" 20 | 200WHEN 1: ="Linux" 21 | 210WHEN 2: ="MacOS" 22 | 220WHEN 3: ="Android" 23 | 230WHEN 4: ="iOS" 24 | 240ENDCASE 25 | 250="Unknown" 26 | 260DEFPROCmatrix 27 | 270SYS "Brandy_Platform" TO os$,cpu$,b64%,sdl%,mactype%,legacy% 28 | 280PRINT "Running on Matrix Brandy on ";os$;" on "; 29 | 290IF b64% THEN PRINT "64-bit "; ELSE PRINT "32-bit "; 30 | 300PRINT cpu$;" with"; 31 | 310IF sdl% THEN PRINT " "; ELSE PRINT "out "; 32 | 320PRINT "SDL graphics." 33 | 330PRINT "Additional info: Uses ";FNmactype;" files on host type ";FNlegacy(legacy%);" (&";~legacy%;")" 34 | 340ENDPROC 35 | 350DEF FNmactype 36 | 360REM Can't use CASE...WHEN..ENDCASE as we can't guarantee modern BASIC. 37 | 370IF mactype% = 0 THEN ="Acorn Electron or Communicator" 38 | 380IF mactype% = 1 THEN ="BBC A/B" 39 | 390IF mactype% = 2 THEN ="BBC B+" 40 | 400IF mactype% = 3 THEN ="BBC Master 128" 41 | 410IF mactype% = 4 THEN ="BBC Master ET" 42 | 420IF mactype% = 5 THEN ="BBC Master Compact" 43 | 430IF mactype% = 6 THEN ="Arthur or RISC OS" 44 | 440IF mactype% = 7 THEN ="Springboard" 45 | 450IF mactype% = 8 THEN ="UNIX-like" 46 | 460IF mactype% = 9 OR mactype% = 17 OR mactype% = 39 THEN ="6809/6309 system" 47 | 470IF mactype% = 10 THEN ="MacOS X" 48 | 480IF mactype% = 28 THEN ="Commodore 64/128" 49 | 490IF mactype% = 29 THEN ="Texas Instruments calculator" 50 | 500IF mactype% = 30 THEN ="Amstrad CPC" 51 | 510IF mactype% = 31 THEN ="Sinclair ZX Spectrum" 52 | 520IF mactype% = 32 THEN ="DOS/Windows" 53 | 530="Unknown" 54 | 540DEF FNlegacy(l%) 55 | 550REM Primarily based on the INKEY-256 value, but uses the OSBYTE&00 value to try to disambiguate 56 | 560IF l% = &FF THEN ="BBC Micro OS 1.00/1.20/1.23 / Reuters OS R0.3 with *UK" 57 | 570IF l% = &FE AND mactype%=8 THEN ="NetBSD" 58 | 580IF l% = &FE THEN ="BBC Micro OS A1.0 / Reuters OS R0.3 with *US" 59 | 590IF l% = &FD THEN ="BBC Master 128 MOS 3.20/3.50" 60 | 600IF l% = &FC THEN ="Microsoft Windows" 61 | 610IF l% = &FB AND mactype%=8 THEN ="BeOS" 62 | 620IF l% = &FB THEN ="BBC B+ 64/128 OS 2.00" 63 | 630IF l% = &FA AND mactype%=32 THEN ="DOS+DJGPP" 64 | 640IF l% = &FA THEN ="Acorn Business Computer / Cambridge Workstation" 65 | 650IF l% = &F9 AND mactype%=8 THEN ="Linux" 66 | 660IF l% = &F9 THEN ="Acorn Communicator" 67 | 670IF l% = &F8 THEN ="MacOS X" 68 | 680IF l% = &F7 AND mactype%=8 THEN ="FreeBSD" 69 | 690IF l% = &F7 THEN ="BBC Master ET MOS 4" 70 | 700IF l% = &F6 THEN ="OpenBSD" 71 | 710IF l% = &F5 AND mactype%=8 THEN ="Amiga" 72 | 720IF l% = &F5 THEN ="BBC Master Compact MOS 5" 73 | 730IF l% = &F4 AND mactype%=8 THEN ="GNU FreeBSD" 74 | 740IF l% = &F4 THEN ="BBC Master 128 MOS 3.26" 75 | 750IF l% = &F3 THEN ="GNU Hurd" 76 | 760IF (l% AND &F0) = &E0 THEN ="Sinclair ZX Spectrum" 77 | 770IF (l% AND &F0) = &D0 THEN ="Amstrad CPC464/664/6128" 78 | 780IF l% = &B7 THEN ="PDP11 Unix Version 7" 79 | 790IF l% = &B6 THEN ="PDP11 Unix version 6" 80 | 800IF l% = &AF THEN ="Springboard" 81 | 810IF l% = &AE THEN ="RISC OS Pyromaniac" 82 | 820IF l% = &AA THEN ="RISC OS 5.xx" 83 | 830IF l% = &A9 THEN ="RISC OS 4.3x" 84 | 840IF l% = &A8 THEN ="RISC OS 4.0x" 85 | 850IF l% = &A7 THEN ="RISC OS 3.7x" 86 | 860IF l% = &A6 THEN ="RISC OS 3.60" 87 | 870IF l% = &A5 THEN ="RISC OS 3.50" 88 | 880IF l% = &A4 THEN ="RISC OS 3.1x" 89 | 890IF l% = &A3 THEN ="RISC OS 3.0x" 90 | 900IF l% = &A2 THEN ="RISC OS 2.01" 91 | 910IF l% = &A1 THEN ="RISC OS 2.00" 92 | 920IF l% = &A0 THEN ="Arthur 1.20" 93 | 930IF l% = &84 THEN ="TI-84+(SE)" 94 | 940IF l% = &83 THEN ="TI-83+(SE)" 95 | 950IF l% = &68 THEN ="6809 system" 96 | 960IF l% = &63 THEN ="6309 system" 97 | 970IF l% = &01 THEN ="Acorn Electron" 98 | 980IF l% = &00 THEN ="BBC Micro OS 0.10 or RM Nimbus" 99 | 990="Unknown" 100 | -------------------------------------------------------------------------------- /docs/Config.txt: -------------------------------------------------------------------------------- 1 | Matrix Brandy configuration file 2 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 3 | 4 | Matrix Brandy now supports the use of a configuration file, which 5 | supports most of the command-line options listed in 'brandy -help' 6 | and additionally some tunables ordinarily set via the SYS command 7 | at run-time. 8 | 9 | The location of this configuration is: 10 | RISC OS: .brandyrc 11 | Windows: %APPDATA%\brandyrc 12 | UNIX/Linux: $HOME/.brandyrc 13 | 14 | These are: 15 | size Set the size of the Basic workspace to bytes 16 | when starting the interpreter. The minimum size 17 | allowed is 16384 bytes and anything below this value 18 | will be set to it. The maximum size is 4294966272 19 | bytes (1K short of 4GB), The size may have a 20 | suffix of 'k', 'm' or 'g' to denote that the size is 21 | in kilobytes, megabytes or gigabytes respectively, for 22 | example, '-size 100k' will set the workspace size to 23 | 100 kilobytes (102400 bytes) and '-size 8m' will set 24 | it to eight megabytes (8388608 bytes). 25 | 26 | nocheck Don't try to check for new versions of Brandy on 27 | interactive mode startup. This is perhaps useful if 28 | you have a slow internet connection that causes Brandy 29 | to hang for a few seconds on startup as it tries to 30 | check for a new version. 31 | 32 | fullscreen (SDL build only) Start Brandy in fullscreen mode. 33 | 34 | nofull (SDL build only) Never use fullscreen mode. 35 | 36 | swsurface (SDL build only) Use a software SDL surface. 37 | 38 | zoom (SDL build only) Zoom the display window by integer 39 | , in the range 1-4. 40 | 41 | tek (Text-mode 'tbrandy' build only) Enable Tektronics 42 | graphics. 43 | 44 | startupmode (SDL build only) Sets the start-up screen mode. 45 | Any built-in mode can be selected by its mode number. 46 | (See ScreenModes.txt) 47 | 48 | path This specifies a list of directories that the 49 | interpreter will search when looking for libraries and 50 | programs. The directory names are separated by commas. 51 | The pseudo-variable 'FILEPATH$' is set to this value. 52 | See the section below on FILEPATH$ for more details. 53 | 54 | lib Load Basic library when the interpreter 55 | starts. This option can be repeated as many times as 56 | required to load a number of libraries. This is 57 | equivalent to typing 'INSTALL ' at the 58 | interpreter's command line. The libraries are loaded 59 | in the order given on the command line. Note that the 60 | search order is the reverse of this. 61 | 62 | ignore (If strict mode enabled by default) Ignore certain 63 | 'unsupported feature' errors. 64 | This option allows some unsupported features that do 65 | not affect the basic running of the program to be 66 | ignored. 67 | 68 | strict (If ignore mode enabled by default) The interpreter 69 | will report an error whenever it comes across a 70 | BASIC V/VI feature that it does not support, and 71 | some obvious BASIC program bugs that are ignored by 72 | the Acorn interpreter. 73 | 74 | lowercase Allow use of lower-case keywords. Unless LISTO option 75 | is set, LIST will show keywords in uppercase. SAVE 76 | will always save keywords in uppercase. 77 | 78 | nostar Do not check commands issued via OSCLI to see if they 79 | are dealt with by Brandy. Pass all commands to the 80 | underlying operating system. 81 | 82 | hex64 Equivalent to SYS"Brandy_Hex64",1. 83 | This controls whether Brandy renders and interprets 84 | Base 16 (Hexadecimal) values as 64-bit. 85 | 86 | bitshift64 This controls whether Brandy calculates bit shifts 87 | in 64-bit space. 32-bit space is used when disabled 88 | as per ARM BBC BASIC V/VI. 89 | 90 | intusesfloat Equivalent to SYS"Brandy_INTusesFloat",1. 91 | This enables a BB4W/BBCSDL extension that allows INT() 92 | to handle numbers > 2^31-1 by using a float if the 93 | number is out of range for a 32-bit signed integer. 94 | 95 | legacyintmaths Equivalent to SYS"Brandy_LegacyIntMaths",1. 96 | This allows integer mathematics to be handled in the 97 | way BBC BASIC 1 to 4 on the Acorn 8-bit machines, and 98 | RISC OS ARM BBC BASIC V, including the rather 99 | questionable wrap-around on integers. RISC OS ARM BBC 100 | BASIC VI, BB4W and BBCSDL do not have this wrap-around 101 | issue and will promote to float when needed. 102 | 103 | pseudovarsunsigned Equivalent to SYS"Brandy_PseudovarsUnsigned",1. 104 | Only effective on 32-bit hardware. Toggles whether 105 | memory pseudo-variables (e.g. PAGE, HIMEM etc) return 106 | large positive numbers above &7FFFFFFF. 107 | 108 | Each option is to be listed on its own line. 109 | 110 | Unrecognised options are silently ignored. A - prefix of any option is 111 | also ignored and also skipped over, so either 112 | -nofull 113 | or 114 | nofull 115 | are equally valid. Similarly, a parameter is separated from its option by 116 | either a single space or a single '=' character. 117 | -------------------------------------------------------------------------------- /docs/keymap.txt: -------------------------------------------------------------------------------- 1 | *FX254,128 is set by default to set the keyboard map to match the OSBYTE 0 value. 2 | *FX254,192 forces the keymap to match the RISC OS keyboard map. 3 | 4 | 5 | RISC OS Keymap - OSBYTE 0 = %000x0xxx, Acorn hardware/MOS or forced with *FX254,192 (b6=1) 6 | ========================================================================================== 7 | 8 | +===+======+======+=====+=====+=====+=====+=====+=====+======+=====+=======+=====+=====+=====+======+======+ 9 | | | 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | A | B | C | D | E | F | 10 | +===+======+======+=====+=====+=====+=====+=====+=====+======+=====+=======+=====+=====+=====+======+======+ 11 | |00x| | | | | | | | | BS | Tab | | | |Retrn| | | 12 | +---+------+------+-----+-----+-----+-----+-----+-----+------+-----+-------+-----+-----+-----+------+------+ 13 | |01x| | | | | | | | | | | | Esc | | | Home | | 14 | +---+------+------+-----+-----+-----+-----+-----+-----+------+-----+-------+-----+-----+-----+------+------+ 15 | +---+------+------+-----+-----+-----+-----+-----+-----+------+-----+-------+-----+-----+-----+------+------+ 16 | |07x| | | | | | | | | | | | | | | | Del | 17 | +---+------+------+-----+-----+-----+-----+-----+-----+------+-----+-------+-----+-----+-----+------+------+ 18 | |18x| F0 | F1 | F2 | F3 | F4 | F5 | F6 | F7 | F8 | F9 | Tab | End | <- | -> | Dn | Up | 19 | | | Prnt | | | | | | | | | | Break | | | | sPgDn| sPgUp| 20 | +---+------+------+-----+-----+-----+-----+-----+-----+------+-----+-------+-----+-----+-----+------+------+ 21 | |19x| sF0 | sF1 | sF2 | sF3 | sF4 | sF5 | sF6 | sF7 | sF8 | sF9 | sTab | sEnd| s<- | s-> | sDn | sUp | 22 | | |sPrnt | | | | | | | | | | sBreak| | | | PgDn | PgUp | 23 | +---+------+------+-----+-----+-----+-----+-----+-----+------+-----+-------+-----+-----+-----+------+------+ 24 | |1Ax| cF0 | cF1 | cF2 | cF3 | cF4 | cF5 | cF6 | cF7 | cF8 | cF9 | cTab | cEnd| c<- | c-> | cDn | cUp | 25 | | |cPrnt | | | | | | | | | | cBreak| | | |scPgDn|scPgUp| 26 | +---+------+------+-----+-----+-----+-----+-----+-----+------+-----+-------+-----+-----+-----+------+------+ 27 | |1Bx| scF0 | scF1 |scF2 |scF3 |scF4 |scF5 |scF6 |scF7 | scF8 |scF9 | scTab |scEnd|sc<- |sc-> | scDn | scUp | 28 | | |scPrnt| | | | | | | | | |scBreak| | | | cPgDn| cPgUp| 29 | +---+------+------+-----+-----+-----+-----+-----+-----+------+-----+-------+-----+-----+-----+------+------+ 30 | |1Cx| LWin| Menu | | | | | | | | | F10 | F11 | F12 | Ins | MsDn | MsUp | 31 | | | sRWin| | | | | | | | | | | | | | | | 32 | +---+------+------+-----+-----+-----+-----+-----+-----+------+-----+-------+-----+-----+-----+------+------+ 33 | |1Dx| sLWin| sMenu| | | | | | | | | sF10 | sF11| sF12| sIns|sMsDn |sMsUp | 34 | | | RWin| | | | | | | | | | | | | | | | 35 | +---+------+------+-----+-----+-----+-----+-----+-----+------+-----+-------+-----+-----+-----+------+------+ 36 | |1Ex| cLWin| cMenu| | | | | | | | | cF10 | cF11| cF12| cIns|cMsDn |cMsUp | 37 | | |scRWin| | | | | | | | | | | | | | | | 38 | +---+------+------+-----+-----+-----+-----+-----+-----+------+-----+-------+-----+-----+-----+------+------+ 39 | |1Fx|scLWin|scMenu| | | | | | | | | scF10 |scF11|scF12|scIns|scMsDn|scMsUp| 40 | | | cRWin| | | | | | | | | | | | | | | | 41 | +---+------+------+-----+-----+-----+-----+-----+-----+------+-----+-------+-----+-----+-----+------+------+ 42 | 43 | 44 | Regular Keymap - OSBYTE 0 <>%000x0xxx, non-Acorn hardware default with *FX254,128 (b6=0) 45 | ======================================================================================== 46 | 47 | +===+=====+=====+===+===+===+===+====+====+=====+====+======+=====+====+====+=====+=====+ 48 | | | 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | A | B | C | D | E | F | 49 | +===+=====+=====+===+===+===+===+====+====+=====+====+======+=====+====+====+=====+=====+ 50 | |00x| | | | | | | | | BS | Tab| | | | Ret| | | 51 | +---+-----+-----+---+---+---+---+----+----+-----+----+------+-----+----+----+-----+-----+ 52 | |01x| | | | | | | | | | | | Esc | | | | | 53 | +---+-----+-----+---+---+---+---+----+----+-----+----+------+-----+----+----+-----+-----+ 54 | +---+-----+-----+---+---+---+---+----+----+-----+----+------+-----+----+----+-----+-----+ 55 | |07x| | | | | | | | | | | | | | | | Del | 56 | +---+-----+-----+---+---+---+---+----+----+-----+----+------+-----+----+----+-----+-----+ 57 | |18x| Prnt| F1 | F2| F3| F4| F5| F6 | F7 | F8 | F9 | F10 | F11 | F12| F13| F14 | F15 | 58 | +---+-----+-----+---+---+---+---+----+----+-----+----+------+-----+----+----+-----+-----+ 59 | |19x|sPrnt| sF1 |sF2|sF3|sF4|sF5| sF6| sF7| sF8 | sF9| sF10 | sF11|sF12|sF13|sF14 |sF15 | 60 | +---+-----+-----+---+---+---+---+----+----+-----+----+------+-----+----+----+-----+-----+ 61 | |1Ax|cPrnt| cF1 |cF2|cF3|cF4|cF5| cF6| cF7| cF8 | cF9| cF10 | cF11|cF12|cF13|cF14 |cF15 | 62 | +---+-----+-----+---+---+---+---+----+----+-----+----+------+-----+----+----+-----+-----+ 63 | |1Bx|aPrnt| aF1 |aF2|aF3|aF4|aF5| aF6| aF7| aF8 | aF9| aF10 | aF11|aF12|aF13|aF14 |aF15 | 64 | +---+-----+-----+---+---+---+---+----+----+-----+----+------+-----+----+----+-----+-----+ 65 | |1Cx| Win | Menu| | | | | Ins| Del| Home| End| PgDn | PgUp| <- | -> | Dn | Up | 66 | +---+-----+-----+---+---+---+---+----+----+-----+----+------+-----+----+----+-----+-----+ 67 | |1Dx|sWin |sMenu| | | | |sIns|sDel|sHome|sEnd|sPgDn |sPgUp| s<-| s->| sDn | sUp | 68 | +---+-----+-----+---+---+---+---+----+----+-----+----+------+-----+----+----+-----+-----+ 69 | |1Ex|cWin |cMenu| | | | |cIns|cDel|cHome|cEnd|cPgDn |cPgUp| c<-| c->| cDn | cUp | 70 | +---+-----+-----+---+---+---+---+----+----+-----+----+------+-----+----+----+-----+-----+ 71 | |1Fx|aWin |aMenu| | | | |aIns|aDel|aHome|aEnd|aPgDn |aPgUp| a<-| a->| aDn | aUp | 72 | +---+-----+-----+---+---+---+---+----+----+-----+----+------+-----+----+----+-----+-----+ 73 | 74 | -------------------------------------------------------------------------------- /other-makefiles/makefile.riscos: -------------------------------------------------------------------------------- 1 | # Makefile for brandy under RISC OS (using Norcroft tools) 2 | 3 | CC = cc 4 | LD = link 5 | 6 | CFLAGS = -c -Wc -IC: -g -throwback -DDEBUG 7 | CFLAGS2 = -c -Wc -IC: -throwback 8 | 9 | LDFLAGS = -debug 10 | 11 | LIBS = C:o.stubs 12 | 13 | OBJ = variables.o tokens.o riscos.o strings.o statement.o \ 14 | stack.o miscprocs.o mainstate.o lvalue.o keyboard.o iostate.o \ 15 | heap.o functions.o fileio.o evaluate.o errors.o emulate.o editor.o \ 16 | convert.o commands.o brandy.o assign.o 17 | 18 | SRC = variables.c tokens.c riscos.c strings.c statement.c \ 19 | stack.c miscprocs.c mainstate.c lvalue.c keyboard.c iostate.c \ 20 | heap.c functions.c fileio.c evaluate.c errors.c emulate.c editor.c \ 21 | convert.c commands.c brandy.c assign.c 22 | 23 | brandy: $(OBJ) 24 | $(LD) $(LDFLAGS) -o brandy $(OBJ) $(LIBS) 25 | 26 | # Build VARIABLES.C 27 | VARIABLES_C = common.h target.h basicdefs.h \ 28 | variables.h evaluate.h tokens.h \ 29 | stack.h heap.h errors.h \ 30 | miscprocs.h screen.h lvalue.h 31 | 32 | variables.o: $(VARIABLES_C) variables.c 33 | $(CC) $(CFLAGS) variables.c 34 | 35 | # Build TOKENS.C 36 | TOKENS_C = common.h target.h basicdefs.h \ 37 | tokens.h miscprocs.h convert.h \ 38 | errors.h 39 | 40 | tokens.o: $(TOKENS_C) tokens.c 41 | $(CC) $(CFLAGS) tokens.c 42 | 43 | # Build RISCOS.C 44 | RISCOS_C = common.h target.h basicdefs.h \ 45 | errors.h scrcommon.h screen.h \ 46 | keyboard.h 47 | 48 | riscos.o: $(RISCOS_C) riscos.c 49 | $(CC) $(CFLAGS) riscos.c 50 | 51 | # Build STRINGS.C 52 | STRINGS_C = common.h target.h basicdefs.h \ 53 | strings.h heap.h errors.h 54 | 55 | strings.o: $(STRINGS_C) strings.c 56 | $(CC) $(CFLAGS) strings.c 57 | 58 | # Build STATEMENT.C 59 | STATEMENT_C = common.h target.h basicdefs.h \ 60 | tokens.h commands.h stack.h \ 61 | heap.h errors.h editor.h \ 62 | miscprocs.h variables.h evaluate.h \ 63 | screen.h fileio.h strings.h \ 64 | iostate.h mainstate.h assign.h \ 65 | statement.h 66 | 67 | statement.o: $(STATEMENT_C) statement.c 68 | $(CC) $(CFLAGS) statement.c 69 | 70 | # Build STACK.C 71 | STACK_C = common.h target.h basicdefs.h \ 72 | stack.h miscprocs.h strings.h \ 73 | tokens.h errors.h 74 | 75 | stack.o: $(STACK_C) stack.c 76 | $(CC) $(CFLAGS) stack.c 77 | 78 | # Build MISCPROCS.C 79 | MISCPROCS_C = common.h target.h basicdefs.h \ 80 | tokens.h errors.h keyboard.h \ 81 | screen.h miscprocs.h 82 | 83 | miscprocs.o: $(MISCPROCS_C) miscprocs.c 84 | $(CC) $(CFLAGS) miscprocs.c 85 | 86 | # Build MAINSTATE.C 87 | MAINSTATE_C = common.h target.h basicdefs.h \ 88 | tokens.h variables.h stack.h \ 89 | heap.h strings.h errors.h \ 90 | statement.h evaluate.h convert.h \ 91 | miscprocs.h editor.h emulate.h \ 92 | screen.h lvalue.h fileio.h \ 93 | mainstate.h 94 | 95 | mainstate.o: $(MAINSTATE_C) mainstate.c 96 | $(CC) $(CFLAGS) mainstate.c 97 | 98 | # Build LVALUE.C 99 | LVALUE_C = common.h target.h basicdefs.h \ 100 | tokens.h evaluate.h stack.h \ 101 | errors.h variables.h miscprocs.h \ 102 | lvalue.h 103 | 104 | lvalue.o: $(LVALUE_C) lvalue.c 105 | $(CC) $(CFLAGS) lvalue.c 106 | 107 | # Build KEYBOARD.C 108 | KEYBOARD_C = common.h target.h basicdefs.h \ 109 | errors.h keyboard.h screen.h 110 | 111 | keyboard.o: $(KEYBOARD_C) keyboard.c 112 | $(CC) $(CFLAGS) keyboard.c 113 | 114 | # Build IOSTATE.C 115 | IOSTATE_C = common.h target.h basicdefs.h \ 116 | tokens.h stack.h strings.h \ 117 | errors.h miscprocs.h evaluate.h \ 118 | convert.h emulate.h fileio.h \ 119 | screen.h lvalue.h statement.h \ 120 | iostate.h 121 | 122 | iostate.o: $(IOSTATE_C) iostate.c 123 | $(CC) $(CFLAGS) iostate.c 124 | 125 | # Build HEAP.C 126 | HEAP_C = common.h target.h basicdefs.h \ 127 | heap.h target.h errors.h \ 128 | miscprocs.h 129 | 130 | heap.o: $(HEAP_C) heap.c 131 | $(CC) $(CFLAGS) heap.c 132 | 133 | # Build FUNCTIONS.C 134 | FUNCTIONS_C = common.h target.h basicdefs.h \ 135 | tokens.h variables.h strings.h \ 136 | convert.h stack.h errors.h \ 137 | evaluate.h keyboard.h screen.h \ 138 | emulate.h miscprocs.h fileio.h \ 139 | functions.h 140 | 141 | functions.o: $(FUNCTIONS_C) functions.c 142 | $(CC) $(CFLAGS) functions.c 143 | 144 | # Build FILEIO.C 145 | FILEIO_C = common.h target.h basicdefs.h \ 146 | errors.h fileio.h strings.h 147 | 148 | fileio.o: $(FILEIO_C) fileio.c 149 | $(CC) $(CFLAGS) fileio.c 150 | 151 | # Build EVALUATE.C 152 | EVALUATE_C = common.h target.h basicdefs.h \ 153 | tokens.h variables.h lvalue.h \ 154 | strings.h stack.h errors.h \ 155 | evaluate.h statement.h miscprocs.h \ 156 | functions.h 157 | 158 | evaluate.o: $(EVALUATE_C) evaluate.c 159 | $(CC) $(CFLAGS) evaluate.c 160 | 161 | # Build ERRORS.C 162 | ERRORS_C = common.h target.h basicdefs.h \ 163 | errors.h stack.h fileio.h keyboard.h \ 164 | tokens.h screen.h miscprocs.h 165 | 166 | errors.o: $(ERRORS_C) errors.c 167 | $(CC) $(CFLAGS) errors.c 168 | 169 | # Build EMULATE.C 170 | EMULATE_C = common.h target.h errors.h \ 171 | basicdefs.h target.h emulate.h \ 172 | screen.h 173 | 174 | emulate.o: $(EMULATE_C) emulate.c 175 | $(CC) $(CFLAGS) emulate.c 176 | 177 | # Build EDITOR.C 178 | EDITOR_C = common.h target.h basicdefs.h \ 179 | errors.h variables.h heap.h \ 180 | tokens.h strings.h miscprocs.h \ 181 | stack.h fileio.h 182 | 183 | editor.o: $(EDITOR_C) editor.c 184 | $(CC) $(CFLAGS) editor.c 185 | 186 | # Build CONVERT.C 187 | CONVERT_C = common.h target.h basicdefs.h \ 188 | convert.h errors.h miscprocs.h 189 | 190 | convert.o: $(CONVERT_C) convert.c 191 | $(CC) $(CFLAGS) convert.c 192 | 193 | # Build COMMANDS.C 194 | COMMANDS_C = common.h target.h basicdefs.h \ 195 | miscprocs.h tokens.h statement.h \ 196 | variables.h editor.h errors.h \ 197 | heap.h stack.h strings.h \ 198 | evaluate.h screen.h keyboard.h 199 | 200 | commands.o: $(COMMANDS_C) commands.c 201 | $(CC) $(CFLAGS) commands.c 202 | 203 | # Build BRANDY.C 204 | BRANDY_C = common.h target.h basicdefs.h \ 205 | tokens.h errors.h heap.h \ 206 | editor.h commands.h statement.h \ 207 | fileio.h emulate.h keyboard.h \ 208 | screen.h miscprocs.h 209 | 210 | brandy.o: $(BRANDY_C) brandy.c 211 | $(CC) $(CFLAGS) brandy.c 212 | 213 | # Build ASSIGN.C 214 | ASSIGN_C = common.h target.h basicdefs.h \ 215 | target.h tokens.h heap.h \ 216 | stack.h strings.h variables.h \ 217 | errors.h miscprocs.h editor.h \ 218 | evaluate.h lvalue.h statement.h \ 219 | assign.h fileio.h emulate.h 220 | 221 | assign.o: $(ASSIGN_C) assign.c 222 | $(CC) $(CFLAGS) assign.c 223 | 224 | recompile: 225 | $(CC) $(CFLAGS) $(SRC) 226 | $(LD) $(LDFLAGS) $(OBJ) $(LIBS) -o brandy 227 | 228 | clean: 229 | wipe o.* ~CF~R~V 230 | wipe brandy ~CF~R~V 231 | wipe map ~CF~R~V 232 | 233 | nodebug: 234 | $(CC) $(CFLAGS2) $(SRC) 235 | $(LD) $(OBJ) $(LIBS) -o brandy -sym map 236 | squeeze brandy 237 | 238 | all: brandy 239 | -------------------------------------------------------------------------------- /other-makefiles/makefile.riscos.gcc: -------------------------------------------------------------------------------- 1 | # Makefile for brandy under RISC OS using GCC 2 | 3 | CC = gcc 4 | LD = ld 5 | 6 | #CFLAGS1 = -w -c -O2 -DBRANDY_DEFAULT_SIZE=512 7 | # Heapsize required for GCC 3.4.6 8 | CFLAGS1 = -w -c --param ggc-min-heapsize=4096 -O2 -DBRANDY_DEFAULT_SIZE=512 9 | CFLAGS2 = -w -c -DNONET -DBRANDY_DEFAULT_SIZE=512 10 | 11 | LDFLAGS1 = 12 | LDFLAGS2 = 13 | 14 | LIBS = gcclib:unixlib gcclib:libscl gcclib:libgcc 15 | 16 | OBJ = o.variables o.tokens o.riscos o.strings o.statement\ 17 | o.stack o.miscprocs o.mainstate o.lvalue o.keyboard o.iostate\ 18 | o.heap o.functions o.fileio o.evaluate o.errors o.mos o.editor\ 19 | o.convert o.commands o.assign o.brandy o.net 20 | 21 | SRC = c.variables c.tokens c.riscos c.strings c.statement\ 22 | c.stack c.miscprocs c.mainstate c.lvalue c.keyboard c.iostate\ 23 | c.heap c.functions c.fileio c.evaluate c.errors c.mos c.editor\ 24 | c.convert c.commands c.assign c.brandy c.net 25 | 26 | brandy: $(OBJ) 27 | $(LD) $(LDFLAGS1) $(OBJ) $(LIBS) -o brandy 28 | 29 | # Build VARIABLES.C 30 | VARIABLES_C = h.common h.target h.basicdefs\ 31 | h.variables h.evaluate h.tokens\ 32 | h.stack h.heap h.errors\ 33 | h.miscprocs h.screen h.lvalue 34 | 35 | o.variables: $(VARIABLES_C) c.variables 36 | $(CC) $(CFLAGS1) c.variables 37 | 38 | # Build TOKENS.C 39 | TOKENS_C = h.common h.target h.basicdefs\ 40 | h.tokens h.miscprocs h.convert\ 41 | h.errors 42 | 43 | o.tokens: $(TOKENS_C) c.tokens 44 | $(CC) $(CFLAGS1) c.tokens 45 | 46 | # Build RISCOS.C 47 | RISCOS_C = h.common h.target h.basicdefs\ 48 | h.errors h.scrcommon h.screen\ 49 | h.keyboard 50 | 51 | o.riscos: $(RISCOS_C) c.riscos 52 | $(CC) $(CFLAGS1) c.riscos 53 | 54 | # Build STRINGS.C 55 | STRINGS_C = h.common h.target h.basicdefs\ 56 | h.strings h.heap h.errors 57 | 58 | o.strings: $(STRINGS_C) c.strings 59 | $(CC) $(CFLAGS1) c.strings 60 | 61 | # Build STATEMENT.C 62 | STATEMENT_C = h.common h.target h.basicdefs\ 63 | h.tokens h.commands h.stack\ 64 | h.heap h.errors h.editor\ 65 | h.miscprocs h.variables h.evaluate\ 66 | h.screen h.fileio h.strings\ 67 | h.iostate h.mainstate h.assign\ 68 | h.statement 69 | 70 | o.statement: $(STATEMENT_C) c.statement 71 | $(CC) $(CFLAGS1) c.statement 72 | 73 | # Build STACK.C 74 | STACK_C = h.common h.target h.basicdefs\ 75 | h.stack h.miscprocs h.strings\ 76 | h.tokens h.errors 77 | 78 | o.stack: $(STACK_C) c.stack 79 | $(CC) $(CFLAGS1) c.stack 80 | 81 | # Build MISCPROCS.C 82 | MISCPROCS_C = h.common h.target h.basicdefs\ 83 | h.tokens h.errors h.keyboard\ 84 | h.screen h.miscprocs 85 | 86 | o.miscprocs: $(MISCPROCS_C) c.miscprocs 87 | $(CC) $(CFLAGS1) c.miscprocs 88 | 89 | # Build MAINSTATE.C 90 | MAINSTATE_C = h.common h.target h.basicdefs\ 91 | h.tokens h.variables h.stack\ 92 | h.heap h.strings h.errors\ 93 | h.statement h.evaluate h.convert\ 94 | h.miscprocs h.editor h.mos\ 95 | h.screen h.lvalue h.fileio\ 96 | h.mainstate 97 | 98 | o.mainstate: $(MAINSTATE_C) c.mainstate 99 | $(CC) $(CFLAGS1) c.mainstate 100 | 101 | # Build LVALUE.C 102 | LVALUE_C = h.common h.target h.basicdefs\ 103 | h.tokens h.evaluate h.stack\ 104 | h.errors h.variables h.miscprocs\ 105 | h.lvalue 106 | 107 | o.lvalue: $(LVALUE_C) c.lvalue 108 | $(CC) $(CFLAGS1) c.lvalue 109 | 110 | # Build KEYBOARD.C 111 | KEYBOARD_C = h.common h.target h.basicdefs\ 112 | h.errors h.keyboard h.screen 113 | 114 | o.keyboard: $(KEYBOARD_C) c.keyboard 115 | $(CC) $(CFLAGS1) c.keyboard 116 | 117 | # Build IOSTATE.C 118 | IOSTATE_C = h.common h.target h.basicdefs\ 119 | h.tokens h.stack h.strings\ 120 | h.errors h.miscprocs h.evaluate\ 121 | h.convert h.mos h.fileio\ 122 | h.screen h.lvalue h.statement\ 123 | h.iostate 124 | 125 | o.iostate: $(IOSTATE_C) c.iostate 126 | $(CC) $(CFLAGS1) c.iostate 127 | 128 | # Build HEAP.C 129 | HEAP_C = h.common h.target h.basicdefs\ 130 | h.heap h.target h.errors\ 131 | h.miscprocs 132 | 133 | o.heap: $(HEAP_C) c.heap 134 | $(CC) $(CFLAGS1) c.heap 135 | 136 | # Build FUNCTIONS.C 137 | FUNCTIONS_C = h.common h.target h.basicdefs\ 138 | h.tokens h.variables h.strings\ 139 | h.convert h.stack h.errors\ 140 | h.evaluate h.keyboard h.screen\ 141 | h.mos h.miscprocs h.fileio\ 142 | h.functions 143 | 144 | o.functions: $(FUNCTIONS_C) c.functions 145 | $(CC) $(CFLAGS1) c.functions 146 | 147 | # Build FILEIO.C 148 | FILEIO_C = h.common h.target h.basicdefs\ 149 | h.errors h.fileio h.strings 150 | 151 | o.fileio: $(FILEIO_C) c.fileio 152 | $(CC) $(CFLAGS1) c.fileio 153 | 154 | # Build EVALUATE.C 155 | EVALUATE_C = h.common h.target h.basicdefs\ 156 | h.tokens h.variables h.lvalue\ 157 | h.strings h.stack h.errors\ 158 | h.evaluate h.statement h.miscprocs\ 159 | h.functions 160 | 161 | o.evaluate: $(EVALUATE_C) c.evaluate 162 | $(CC) $(CFLAGS1) c.evaluate 163 | 164 | # Build ERRORS.C 165 | ERRORS_C = h.common h.target h.basicdefs\ 166 | h.errors h.stack h.fileio h.keyboard\ 167 | h.tokens h.screen h.miscprocs 168 | 169 | o.errors: $(ERRORS_C) c.errors 170 | $(CC) $(CFLAGS1) c.errors 171 | 172 | # Build MOS.C 173 | MOS_C = h.common h.target h.errors\ 174 | h.basicdefs h.target h.mos\ 175 | h.screen 176 | 177 | o.mos: $(MOS_C) c.mos 178 | $(CC) $(CFLAGS1) c.mos 179 | 180 | # Build EDITOR.C 181 | EDITOR_C = h.common h.target h.basicdefs\ 182 | h.errors h.variables h.heap\ 183 | h.tokens h.strings h.miscprocs\ 184 | h.stack h.fileio 185 | 186 | o.editor: $(EDITOR_C) c.editor 187 | $(CC) $(CFLAGS1) c.editor 188 | 189 | # Build CONVERT.C 190 | CONVERT_C = h.common h.target h.basicdefs\ 191 | h.convert h.errors h.miscprocs 192 | 193 | o.convert: $(CONVERT_C) c.convert 194 | $(CC) $(CFLAGS1) c.convert 195 | 196 | # Build COMMANDS.C 197 | COMMANDS_C = h.common h.target h.basicdefs\ 198 | h.miscprocs h.tokens h.statement\ 199 | h.variables h.editor h.errors\ 200 | h.heap h.stack h.strings\ 201 | h.evaluate h.screen h.keyboard 202 | 203 | o.commands: $(COMMANDS_C) c.commands 204 | $(CC) $(CFLAGS1) c.commands 205 | 206 | # Build ASSIGN.C 207 | ASSIGN_C = h.common h.target h.basicdefs\ 208 | h.target h.tokens h.heap\ 209 | h.stack h.strings h.variables\ 210 | h.errors h.miscprocs h.editor\ 211 | h.evaluate h.lvalue h.statement\ 212 | h.assign h.fileio h.mos 213 | 214 | o.assign: $(ASSIGN_C) c.assign 215 | $(CC) $(CFLAGS1) c.assign 216 | 217 | # Build BRANDY.C 218 | BRANDY_C = h.common h.target h.basicdefs\ 219 | h.tokens h.errors h.heap\ 220 | h.editor h.commands h.statement\ 221 | h.fileio h.mos h.keyboard\ 222 | h.screen h.miscprocs 223 | 224 | o.brandy: $(BRANDY_C) c.brandy 225 | $(CC) $(CFLAGS1) c.brandy 226 | 227 | # Build NET.C 228 | NET_C = h.target h.errors h.net 229 | 230 | o.net: $(NET_C) c.net 231 | $(CC) $(CFLAGS1) c.net 232 | 233 | recompile: 234 | $(CC) $(CFLAGS1) $(SRC) 235 | $(LD) $(LDFLAGS1) $(OBJ) $(LIBS) -o brandy 236 | 237 | clean: 238 | wi 239 | -------------------------------------------------------------------------------- /docs/osbyte.txt: -------------------------------------------------------------------------------- 1 | OSBYTE and *FX calls 2 | ==================== 3 | 4 | Brandy implements a limited set of OSBYTE calls, either by *FX, CALL &FFF4, 5 | result%=USR &FFF4, or SYS "OS_Byte",A[,X[,Y]] [TO ...]. Where a return value 6 | is supported, it will be &00YYXXAA when called via USR &FFF4. 7 | 8 | OSBYTE 176-255 read and write system variables with 9 | newvalue = (oldvalue AND Y) EOR X 10 | so *FX a,x[,0] and OSBYTE A,X,0 writes the value and OSBYTE A,0,255 reads 11 | the value. Different combinations of X and Y can set and reset individual 12 | bits. 13 | 14 | 15 | Supported OSBYTE calls 16 | ---------------------- 17 | A=0: X=0: return the MOS version as an error with ERR=247. 18 | X<>0: Return the host OS version in the X register (as per the 'use' 19 | doc) 20 | A=6: Sets the default printer ignore character, default is 13. 21 | A=15: Flush keyboard and mouse buffers. 22 | A=20: Resets the system font (SDL build only) 23 | A=21: Flush keyboard or mouse buffer: 24 | X=0: Flush keyboard buffer 25 | X=9: Flush mouse buffer 26 | A=25: Resets parts of the system font (SDL build only) 27 | X=0 or 16 resets the teletext font (16 ONLY does the teletext font) 28 | after being changed with OSWORD 140. 29 | A=42: (Deprecated, see A=163 X=2) 30 | A=43: (Deprecated, see A=163 X=3) 31 | A=44: (Deprecated, see A=163 X=4) 32 | 33 | A=106: Select mouse pointer. Due to SDL limitations, this simply turns the 34 | pointer on or off, and unlinking does nothing. 35 | A=112: Selects which video bank the VDU drivers access. 4 available. 36 | A=113: Selects which video bank is drawn to the display window. 37 | A=128: ADVAL. As with BASIC ADVAL, only some subfuntions supported. 38 | A=129: INKEY. As with BASIC INKEY, scanning for range of keys not 39 | supported. 40 | A=130: High word of user memory. 41 | A=131: Bottom of user memory. 42 | A=132: Top of user memory 43 | A=134: Return text cursor position in X and Y. Identical to 165. 44 | A=135: Return screen mode and character under cursor or 0 if unreadable. 45 | A=160: Read VDU variable (equivalent to VDU(X%)) 46 | A=163: Application Support - X < 128 are local to Brandy 47 | X=1: Get or set refresh state (as per *REFRESH) 48 | Y=0: Equivalent to the old behaviour of *REFRESH OFF 49 | (refresh is not re-enabled on an error condition) 50 | Y=1: Equivalent to *REFRESH ON 51 | Y=2: Equivalent to *REFRESH OFF (and *REFRESH ONERROR) 52 | Y=255: Query the state, will return 0, 1 or 2 in Y register. 53 | X=2: Get or set various states [Brandy only] 54 | If NO bits set: return state in Y register. 55 | If ALL bits set: Analogue of Linux's "stty sane" - enables 56 | Refresh, issues a VDU 6 and sets both video bank 57 | controls to 0. 58 | Bits 0 and 1 control or contain the *REFRESH state: 59 | 00: No operation. 60 | 01: Set with *FX163,1,0 61 | 10: Set with *REFRESH ON 62 | 11: Set with *REFRESH OFF and *REFRESH ONERROR 63 | Returned values: 01, 10 or 11. 64 | Bits 2 and 3 control or contain the Full Screen state: 65 | 00: No operation. 66 | 01: Full Screen Off. 67 | 10: Full Screen On. 68 | 11: Full Screen Toggle. 69 | Returned values: 00 (off) or 10 (on). 70 | Bit 4: If set, do immediate display refresh, equivalent 71 | to *REFRESH 72 | Value not returned. 73 | X=3: Perform a VDU X to the controlling Linux terminal. 74 | X=4: Y=1: CTRL-N and CTRL-P do line editing (default). 75 | Y=0: CTRL-N and CTRL-P just send their codes. 76 | Arrow keys still do line editing. 77 | X=127: Analogue of Linux's "stty sane" - enables Refresh, issues a 78 | VDU 6 and sets both video bank controls to 0. 79 | X=242: Set the line drawing dot pattern style 80 | A=165: Return text cursor position in X and Y. Identical to 134. 81 | 82 | A=200: Set Escape key and Reset effects - only Escape key effect supported. 83 | A=210: Sound disabled if X is non-zero. 84 | A=220: Set TAB character 85 | A=220: Set ESCAPE character 86 | A=229: Enable or disable ESCAPE, disabled if X non-zero. 87 | A=230: Define Escape effects. 88 | A=250: Read and write video bank set with OSBYTE 112, returns bank set with 89 | OSBYTE 113 in Y 90 | A=251: Read and write video bank set with OSBYTE 113. 91 | 92 | OSBYTEs 166-255 read and write OSBYTE system variables with new=(old AND Y) 93 | EOR X, but only those listed have any effect. 94 | 95 | 96 | Keyboard OSBYTEs 97 | ---------------- 98 | INKEY/GET fetches 99 | a keypress 100 | | 101 | Key=TAB ----No-->-+ 102 | | | 103 | Char=OSBYTE(219) | *not yet implemented 104 | | | 105 | +------------<-+ 106 | | 107 | Char=OSBYTE(222) -No-->--------------+ 108 | | | 109 | OSBYTE(229)=0 --No-->--------------+ 110 | | | 111 | OSBYTE(200).b0=0 -No->-+ OSBYTE(254).b6=0 -No->-+ 112 | | | | | 113 | Set Escape state | Translate to | *FX221-*FX228 114 | | | RISC OS key | not yet 115 | +-------------<-+ mapping | implemented 116 | | | | 117 | | +------------+ 118 | | | 119 | Return Return 120 | 'no key' keypress 121 | 122 | The difference between *FX229 and *FX200 is that *FX229,1 results in the 123 | Escape key returning an ASCII character, and *FX200,1 results in the Escape 124 | key not generating an Escape state. 125 | 126 | Escape handler generates an "Escape" error. The error handler then calls the 127 | EscapeAcknowledge code called by OSBYTE 126. This examines OSBYTE 230 to 128 | determine what to do. bit0-bit3 indicate what to do after an Escape, 129 | bit4-bit7 indicate that these actions should be done for all errors, not 130 | just Escapes. The default is &00 to do all Escape actions on Escape only. 131 | 132 | bit 0=0: close Exec, cancel VDU queue, clear sounds, cancel pending 133 | keypresses 134 | bit 1=0: refresh display 135 | bit 2=0: reserved 136 | bit 3=0: reserved 137 | bit 4=1: clear Exec/VDU/Sound/keyboard on errors 138 | bit 5=1: refresh display on errors 139 | bit 6=1: reserved 140 | bit 7=1: reserved 141 | 142 | *FX11/12/196/197 keyboard repeat settings are not implemented. 143 | *FX172/173 to return keyboard translation not implemented 144 | *FX178 keyboard interupt disable not implemented 145 | *FX201 keyboard disable not implemented 146 | *FX202 keyboard status no implemented 147 | *FX221-228 top-bit set translations not implemented 148 | *FX4/237 cursor key settings not implemented 149 | *FX238 keypad base not implemented 150 | *FX240 country not implemented 151 | *FX247 soft Break key effects not implemented 152 | 153 | -------------------------------------------------------------------------------- /docs/extensions.txt: -------------------------------------------------------------------------------- 1 | Extensions to the MOS API called by BBC BASIC 2 | --------------------------------------------- 3 | These are defined extensions, some may or may not be included in Brandy. 4 | 5 | 6 | INKEY(&FF00+nn) - BBC keyscan (standard) 7 | INKEY(&FE00+nn) - DOS keyscan 8 | INKEY(&FC00+nn) - SDL keyscan 9 | INKEY(&8000+nn) - 16-bit INKEY 10 | 11 | ADVAL(n) - read I/O device (standard) 12 | ADVAL(-n) - test buffer contents (standard) 13 | ADVAL(128-n) - low-level read of buffer n 14 | ADVAL(128-1) - fetch untranslated entry from keyboard buffer, 16-bit GET 15 | 16 | BPUT#0 - VDU 17 | BGET#0 - GET 18 | EOF#0 - input pending, soft key being expanded or key in keyboard 19 | buffer (contrast with ADVAL(-1) which only tests keyboard 20 | buffer) 21 | PTR#0 22 | EXT#0 23 | 24 | 25 | COLOUR &00+n - foreground colour (standard) 26 | COLOUR &40+n - reserved (various functionality) 27 | COLOUR &80+n - background colour (standard) 28 | COLOUR &C0+n - border colour 29 | 30 | VDU 19,<128,p,r,g,b - set logical colour 31 | VDU 19,-1 ,p,r,g,b - set border colour (-1 is sent as CHR$255) 32 | 33 | VDU 19,l, 0+RGB ,r,g,b - steady physical colour (standard) 34 | VDU 19,l, 8+RGB ,r,g,b - flashing or bright physical colour (standard) 35 | VDU 19,l, 16+action,r,g,b - RGB colour (standard extension) 36 | VDU 19,l, 32+RGB ,r,g,b - first flashing physical colour 37 | VDU 19,l, 48+RGB ,r,g,b - second flashing physical colour 38 | VDU 19,l, 64+action,r,g,b - reserved 39 | VDU 19,l,128+y ,z,x,x - CPC: 5-bit physical colours y and z 40 | VDU 19,l,255 ,r,g,b - DOS: 6-bit RGB colour 41 | 42 | VDU 23,18,n,setting,mask| - teletext display settings, new setting = 43 | (old setting AND mask) EOR setting 44 | VDU 23,18,0,display,mask| - set mix/box display mode 45 | b1-b0=text/mix/box/TV 46 | VDU 23,18,1,update,mask| - set update type 47 | b0=suspend all automatic display upate 48 | b1=update display after every character 49 | VDU 23,18,2,reveal,mask| - reveal concealed display 50 | b0=reveal concealed characters 51 | VDU 23,18,3,enable,mask| - enable extended control characters 52 | b0=black foreground enabled (CHR$&80, CHR$&90) 53 | b1=double width enable (CHR$&8E, CHR$&8F) 54 | b7-b2=reserved for eg Level 3 features 55 | VDU 23,18,4,fontLo,fontHi| - select teletext font as per SAA505x series. 56 | VDU 23,18,16,quality,mask| - select character display quality 57 | b0=render high quality text 58 | VDU 23,18,255,width| - Set Teletext character cell width. 59 | 60 | VDU 23,22 - define screen mode (BBCSDL) 61 | VDU 23,23 - set line thickness (BBCSDL) 62 | VDU 23,24 - set character spacing (BBCSDL) 63 | VDU 23,31 - reset VDU system (internal to BBCSDL) 64 | 65 | GCOL 0,c GCOL 1,c GCOL 2,c - standard GCOL commands 66 | GCOL 3,c GCOL 4,c 67 | GCOL 5,c - on-screen colour not changed (RISC OS) 68 | GCOL 6,c - on-screen colour = c AND NOT on-screen colour (RISC OS) 69 | GCOL 7,c - on-screen colour = c OR NOT on-screen colour (RISC OS) 70 | GCOL 8+n,c - GCOL n with transparent background (RISC OS) 71 | GCOL 16*p+n,c - Use extended colour pattern p for p=1..4 72 | (GXR, MOS 3) or giant pattern for p=5 (RISC OS) 73 | GCOL 96+,c - reserved 74 | 75 | 76 | Extensions to BBC BASIC 77 | ----------------------- 78 | BPUT#n,byte - put single byte (standard) 79 | BPUT#n,string[;] - put string (standard extension) 80 | BPUT#n,byte[,byte....] - put multiple bytes 81 | 82 | BGET#n - get single byte (standard) 83 | GET$#n - get string (standard extension) 84 | 85 | COLOUR l,p - do VDU 19,l,p,0,0,0 86 | COLOUR l,r,g,b - do VDU 19,l,16,r,g,b or VDU 19,l,24,r,g,b if l<0 87 | GCOL c - do GCOL 0,c 88 | PLOT x,y - do PLOT 69,x,y 89 | =COLOUR(r,g,b) - MODE-dependent colour number closest matching RGB. 90 | =CHR$(x,y) - read character from screen at x,y 91 | SOUND ON - turn sound on (*FX210,0) 92 | SOUND OFF - turn sound off (*FX210,1) 93 | &o - octal constant, eg &o107 94 | % - binary constant, eg %100111 (standard extension) 95 | %% - Variable suffix, to denote a 64-bit integer. 96 | & - Variable suffix, to denote unsigned 8-bit integer. 97 | ] - 64-bit unary indirection. 98 | 99 | DIM HIMEM - A Basalt extension, use to define arrays outside 100 | of heap space using malloc(). Byte arrays defined 101 | this way can be de-allocated by re-DIMming to -1. 102 | 103 | CLEAR HIMEM [] - Deallocate off-heap arrays allocated using DIM HIMEM. 104 | This does not deallocate memory blocks. 105 | 106 | 107 | Notes on ADVAL(-1) and EOF#0 108 | ---------------------------- 109 | ADVAL(-1) returns how many entries are in the keyboard buffer, EOF#0 - where 110 | implemented - returns whether the next GET or INKEY will return immediately. 111 | These are two slightly different concepts. 112 | 113 | If the current input stream is an EXEC file, ADVAL(-1) does not tell you if 114 | tell you if there is a byte to read from GET/INKEY. 115 | 116 | If the current input stream is the serial port, ADVAL(-1) does not tell you 117 | if there is a byte to read from GET/INKEY, the serial input buffer is 118 | ADVAL(-2). 119 | 120 | Subtly, soft keys can give unexpected results. Consider the case where you 121 | have: 122 | *KEY 0 "hello" 123 | *KEY 1 "" 124 | 125 | Assuming the keyboard buffer is empty, if f0 is pressed, ADVAL(-1) will 126 | return 1. GET/INKEY will fetch the "h" character, but thereup ADVAL(-1) will 127 | return 0 - as there is now nothing in the keyboard buffer. However, there 128 | are still four characters that can be fetched as there is a soft key being 129 | expanded. You can see this with this bit of code, press f0 and only a single 130 | character will be displayed: 131 | 132 | REPEAT 133 | IF ADVAL(-1) THEN VDU GET 134 | UNTIL FALSE 135 | 136 | Now assume that f1 has been pressed. ADVAL(-1) will again return 1 as there 137 | is one entry in the keyboard buffer. However, GET will wait forever, as it 138 | will fetch the one entry from the keyboard buffer, find it is a soft key, 139 | find that the soft key defintion is a null string, and loop back waiting for 140 | something to enter the keyboard buffer. Again, with the same sample code, 141 | pressing f1 will cause the program to wait forever - or until another key is 142 | pressed. 143 | 144 | 145 | If EOF#0 is implemented, it should do its best to examine the system and 146 | only return zero if and only if the next GET/INKEY will immediately return 147 | with no waiting, so the following code will work: 148 | 149 | REPEAT 150 | IF NOT EOF#0 THEN VDU GET 151 | UNTIL FALSE 152 | 153 | In general, if you can it is better to write code in the form: 154 | 155 | key%=INKEY(time):IF key%<>-1 THEN .... 156 | 157 | -------------------------------------------------------------------------------- /MatrixBrandy.spec: -------------------------------------------------------------------------------- 1 | Summary: A cross-platform BBC BASIC interpreter with SDL graphics 2 | Name: brandy 3 | Version: 1.23.6 4 | Release: %{extraverdata}.matrix%{?dist} 5 | License: GPLv2+ 6 | Group: Development/Tools 7 | Source: https://brandy.matrixnetwork.co.uk/releases/MatrixBrandy-%{version}.tar.xz 8 | URL: https://brandy.matrixnetwork.co.uk/ 9 | # Dirty hack to ensure we have SDL-devel or sdl12-compat-devel 10 | BuildRequires: /usr/include/SDL/SDL.h 11 | Requires: brandy-docs = %{version}-%{release} 12 | Requires: brandy-examples = %{version}-%{release} 13 | 14 | %define debug_package %{nil} 15 | 16 | %description 17 | Brandy is an interpreter for BBC BASIC VI that runs under a variety of 18 | operating systems. BASIC V and BASIC VI are versions of BASIC supplied with 19 | computers running RISC OS. These were originally made by Acorn Computers and 20 | more recently designed and manufactured by companies such as Advantage Six 21 | and Castle Technology. 22 | 23 | The Matrix Brandy fork includes support for much of the grahics modes 24 | offered by RISC OS including Mode 7 (Teletext), and basic networking 25 | both of which are used by the bundled "telstar" example. Many bugs are fixed 26 | and mathematics are brought more in line with Acorn's BBC BASIC VI. 27 | Some BASIC extensions from Richard Russell's BB4W and BBCSDL are also 28 | supported, as are a few from Steve Drain's Basalt add-on for RISC OS. 29 | 30 | BBC BASIC is a trademark of the British Broadcasting Corporation. 31 | Matrix Brandy does not claim to be "BBC BASIC", however it aims to be an 32 | interpreter of the BBC BASIC dialect of BASIC. The term "BBC BASIC" in 33 | the documentation is used in reference to the dialect, and other 34 | implementations where the name is used under licence (e.g. by Acorn/RISC OS 35 | and the interpreters by Richard Russell). 36 | 37 | %package docs 38 | Summary: Documentation for Matrix Brandy 39 | BuildArch: noarch 40 | 41 | %package examples 42 | Summary: Example programs for Matrix Brandy 43 | BuildArch: noarch 44 | 45 | %package text 46 | Summary: A cross-platform BBC BASIC interpreter (text mode) 47 | Requires: brandy-docs = %{version}-%{release} 48 | Requires: brandy-examples = %{version}-%{release} 49 | 50 | %package telstar 51 | Summary: Desktop launcher for Matrix Brandy's videotex/viewdata client 52 | Requires: brandy = %{version}-%{release} 53 | Requires: brandy-examples = %{version}-%{release} 54 | BuildArch: noarch 55 | 56 | %description docs 57 | This package contains the documentation files for Matrix Brandy. 58 | 59 | %description examples 60 | This package contains the example programs for Matrix Brandy. 61 | 62 | %description telstar 63 | This package contains the desktop shortcut file, icon and launcher script 64 | for Matrix Brandy's Telstar viewdata/videotex client. The Telstar program 65 | itself is one of the examples in the main brandy package, this sub-package 66 | simply provides a GNOME desktop link and icon. 67 | 68 | %description text 69 | Brandy is an interpreter for BBC BASIC VI that runs under a variety of 70 | operating systems. BASIC V and BASIC VI are versions of BASIC supplied with 71 | computers running RISC OS. These were originally made by Acorn Computers and 72 | more recently designed and manufactured by companies such as Advantage Six 73 | and Castle Technology. 74 | 75 | This package contains the text-mode builds of Matrix Brandy, and aside for 76 | Tektronix support with some terminals, these builds do not support graphics. 77 | 78 | BBC BASIC is a trademark of the British Broadcasting Corporation. 79 | Matrix Brandy does not claim to be "BBC BASIC", however it aims to be an 80 | interpreter of the BBC BASIC dialect of BASIC. The term "BBC BASIC" in 81 | the documentation is used in reference to the dialect, and other 82 | implementations where the name is used under licence (e.g. by Acorn/RISC OS 83 | and the interpreters by Richard Russell). 84 | 85 | 86 | 87 | %prep 88 | %setup -q -n MatrixBrandy-%{version} 89 | chmod 0644 docs/* 90 | 91 | %build 92 | make clean %{?_smp_mflags} 93 | make %{?_smp_mflags} 94 | make -f makefile.text clean %{?_smp_mflags} 95 | make -f makefile.text %{?_smp_mflags} 96 | 97 | %install 98 | rm -rf %{buildroot} 99 | mkdir -p %{buildroot}%{_bindir} 100 | mkdir -p %{buildroot}%{_libdir} 101 | mkdir -p %{buildroot}%{_datadir}/%{name}-%{version}/examples 102 | mkdir -p %{buildroot}%{_datadir}/applications 103 | mkdir -p %{buildroot}%{_datadir}/pixmaps 104 | install -s -m 0755 brandy %{buildroot}%{_bindir} 105 | install -s -m 0755 sbrandy %{buildroot}%{_bindir} 106 | install -s -m 0755 tbrandy %{buildroot}%{_bindir} 107 | install -m 0755 desktop/telstar %{buildroot}%{_bindir} 108 | install -m 0644 desktop/brandy.desktop %{buildroot}%{_datadir}/applications 109 | install -m 0644 desktop/telstar.desktop %{buildroot}%{_datadir}/applications 110 | install -m 0644 desktop/brandy.png %{buildroot}%{_datadir}/pixmaps 111 | install -m 0644 desktop/telstar.png %{buildroot}%{_datadir}/pixmaps 112 | cp -r examples/* %{buildroot}%{_datadir}/%{name}-%{version}/examples 113 | 114 | %clean 115 | rm -rf %{buildroot} 116 | 117 | %files 118 | %{_bindir}/brandy 119 | %{_datadir}/pixmaps/brandy.png 120 | %{_datadir}/applications/brandy.desktop 121 | 122 | %files docs 123 | %doc READ.ME docs/ChangeLog docs/README docs/*.txt 124 | 125 | %files examples 126 | %{_datadir}/%{name}-%{version}/examples 127 | 128 | %files telstar 129 | %{_bindir}/telstar 130 | %{_datadir}/pixmaps/telstar.png 131 | %{_datadir}/applications/telstar.desktop 132 | 133 | %files text 134 | %{_bindir}/sbrandy 135 | %{_bindir}/tbrandy 136 | 137 | %changelog 138 | * Fri Jun 20 2025 Michael McConnell - 1.23.6 139 | - Added sub-package "telstar". 140 | * Sat Aug 01 2020 Michael McConnell - 1.22.7 141 | - Removed BrandyApp from package as build mechanism has changed. 142 | * Tue Jul 23 2019 Michael McConnell - 1.22.0 143 | - Re-tag as BASIC VI 144 | * Sun Sep 02 2018 Michael McConnell - 1.21.12 145 | - Build both SDL and text-mode variants. 146 | * Thu Aug 23 2018 Michael McConnell - 1.21.11 147 | - Adapted for Matrix Brandy. 148 | * Fri Nov 18 2016 Huaren Zhong 1.20.1 149 | - Rebuild for Fedora 150 | * Mon Feb 07 2011 Fedora Release Engineering - 1.0.19-9 151 | - Rebuilt for https://fedoraproject.org/wiki/Fedora_15_Mass_Rebuild 152 | * Fri Jul 24 2009 Fedora Release Engineering - 1.0.19-8 153 | - Rebuilt for https://fedoraproject.org/wiki/Fedora_12_Mass_Rebuild 154 | * Mon Feb 23 2009 Fedora Release Engineering - 1.0.19-7 155 | - Rebuilt for https://fedoraproject.org/wiki/Fedora_11_Mass_Rebuild 156 | * Mon Jul 14 2008 Tom "spot" Callaway - 1.0.19-6 157 | - fix license tag 158 | * Tue Feb 19 2008 Fedora Release Engineering - 1.0.19-5 159 | - Autorebuild for GCC 4.3 160 | * Thu Sep 14 2006 Paul F. Johnson - 1.0.19-4 161 | - rebuild 162 | * Wed Aug 16 2006 Paul F. Johnson - 1.0.19-3 163 | - Added perl hack for proper flags going to gcc (Thanks Tibbs) 164 | * Sun Aug 13 2006 Paul F. Johnson - 1.0.19-2 165 | - Fix for examples being correctly copied 166 | - altered %%doc 167 | - corrected initial import date 168 | - added %%defattr 169 | * Thu Aug 10 2006 Paul F. Johnson - 1.0.19-1 170 | - Initial import into FE 171 | -------------------------------------------------------------------------------- /docs/ScreenModes.txt: -------------------------------------------------------------------------------- 1 | The built-in screen modes in Matrix Brandy are based on those from RISC OS, 2 | the first 8 themselves based on the BBC Micro. 3 | 4 | On RISC OS, MODEs 0-63 are available depending on your monitor configuration 5 | and RISC OS version. MODEs 64 and up are not available. On the Risc PC and 6 | later, user-defined modes with the extended MODE command are available, but 7 | handled by RISC OS (and not through MODE 126). *NewMode is not implemented. 8 | 9 | Mode Text resolution Graphics resolution Colours Pixel size Logical res 10 | 0 80x32 640x256 2 1x2 1280x1024 11 | 1 40x32 320x256 4 2x2 1280x1024 12 | 2 20x32 160x256 16 4x2 1280x1024 13 | 3 80x25 Text only 2 1x2 Text only 14 | 4 40x32 320x256 2 2x2 1280x1024 15 | 5 20x32 160x256 4 4x2 1280x1024 16 | 6 40x25 Text only 2 2x2 Text only 17 | 7 40x25 (Teletext mode, this works differently to other modes) 18 | 8 80x32 640x256 4 1x2 1280x1024 19 | 9 40x32 320x256 16 2x2 1280x1024 20 | 10 20x32 160x256 256 4x2 1280x1024 21 | 11 80x25 640x250 4 1x2 1280x1000 22 | 12 80x32 640x256 16 1x2 1280x1024 23 | 13 40x32 320x256 256 2x2 1280x1024 24 | 14 80x25 640x250 16 1x2 1280x1000 25 | 15 80x32 640x256 256 1x2 1280x1024 26 | 16 132x32 1056x256 16 1x2 2112x1024 27 | 17 132x25 1056x250 16 1x2 2112x1000 28 | 18 80x64 640x512 2 1x1 1280x1024 29 | 19 80x64 640x512 4 1x1 1280x1024 30 | 20 80x64 640x512 16 1x1 1280x1024 31 | 21 80x64 640x512 256 1x1 1280x1024 32 | 22 96x36 768x288 16 1x2 768x576 33 | 23 144x112 1152x896 2 1x1 2304x1792 34 | 24 132x32 1056x256 256 1x2 2112x1024 35 | 25 80x60 640x480 2 1x1 1280x960 36 | 26 80x60 640x480 4 1x1 1280x960 37 | 27 80x60 640x480 16 1x1 1280x960 38 | 28 80x60 640x480 256 1x1 1280x960 39 | 29 100x75 800x600 2 1x1 1600x1200 40 | 30 100x75 800x600 4 1x1 1600x1200 41 | 31 100x75 800x600 16 1x1 1600x1200 42 | 32 100x75 800x600 256 1x1 1600x1200 43 | 33 96x36 768x288 2 1x2 1536x1152 44 | 34 96x36 768x288 4 1x2 1536x1152 45 | 35 96x36 768x288 16 1x2 1536x1152 46 | 36 96x36 768x288 256 1x2 1536x1152 47 | 37 112x44 896x352 2 1x2 1792x1408 48 | 38 112x44 896x352 4 1x2 1792x1408 49 | 39 112x44 896x352 16 1x2 1792x1408 50 | 40 112x44 896x352 256 1x2 1792x1408 51 | 41 80x44 640x352 2 1x2 1280x1408 52 | 42 80x44 640x352 4 1x2 1280x1408 53 | 43 80x44 640x352 16 1x2 1280x1408 54 | 44 80x25 640x200 2 1x2 1280x800 55 | 45 80x25 640x200 4 1x2 1280x800 56 | 46 80x25 640x200 16 1x2 1280x800 57 | 47 45x60 360x480 256 2x1 1280x800 58 | 48 40x60 320x480 16 2x1 1280x960 59 | 49 40x60 320x480 256 2x1 1280x960 60 | 50 40x30 320x240 2 2x2 1280x960 61 | 51 40x30 320x240 4 2x2 1280x960 62 | 52 40x30 320x240 16 2x2 1280x960 63 | 53 40x30 320x240 256 2x2 1280x960 64 | 54-63 reserved for future expansion within RISC OS. 65 | Modes from 64 are only available on SDL builds, and can be redefined with 66 | *NewMode, these definitions are local to Matrix Brandy, and may be changed 67 | in the future. As such they are not available on RISC OS, however the 68 | new-style MODE commands are available and can be used to replicate these. 69 | Modes 64-68 use the same coordinate system as Tektronix graphical terminals 70 | 64 128x97 1024x780 2 1x1 2048x1560 71 | 65 128x97 1024x780 4 1x1 2048x1560 72 | 66 128x97 1024x780 16 1x1 2048x1560 73 | 67 128x97 1024x780 256 1x1 2048x1560 74 | 68 128x97 1024x780 16777216 1x1 2048x1560 75 | Modes 69-93 are widescreen modes, possibly useful for full-screen use. 76 | 69 128x72 1024x576 2 1x1 2048x1152 77 | 70 128x72 1024x576 4 1x1 2048x1152 78 | 71 128x72 1024x576 16 1x1 2048x1152 79 | 72 128x72 1024x576 256 1x1 2048x1152 80 | 73 128x72 1024x576 16777216 1x1 2048x1152 81 | 74 170x48 1360x384 2 1x2 2720x1536 82 | 75 170x48 1360x384 4 1x2 2720x1536 83 | 76 170x48 1360x384 16 1x2 2720x1536 84 | 77 170x48 1360x384 256 1x2 2720x1536 85 | 78 170x48 1360x384 16777216 1x2 2720x1536 86 | 79 170x96 1360x768 2 1x1 2720x1536 87 | 80 170x96 1360x768 4 1x1 2720x1536 88 | 81 170x96 1360x768 16 1x1 2720x1536 89 | 82 170x96 1360x768 256 1x1 2720x1536 90 | 83 170x96 1360x768 16777216 1x1 2720x1536 91 | 84 240x67 1920x540 2 1x2 3840x2160 92 | 85 240x67 1920x540 4 1x2 3840x2160 93 | 86 240x67 1920x540 16 1x2 3840x2160 94 | 87 240x67 1920x540 256 1x2 3840x2160 95 | 88 240x67 1920x540 16777216 1x2 3840x2160 96 | 89 240x135 1920x1080 2 1x1 3840x2160 97 | 90 240x135 1920x1080 4 1x1 3840x2160 98 | 91 240x135 1920x1080 16 1x1 3840x2160 99 | 92 240x135 1920x1080 256 1x1 3840x2160 100 | 93 240x135 1920x1080 16777216 1x1 3840x2160 101 | 102 | 103 | Note 1: MODEs 22 and 35 differ in that MODE 22 uses a non-standard pixel 104 | addressing with a 768x288 display on a 768x576 pixel addressing range, 105 | while MODE 35 uses the more standard doubling of 1536x1152. 106 | Note 2: COLOUR/GCOL numbers and TINT in 24-bit colour modes give the same 107 | colours as 256-colour modes. Using the newer form of COLOUR r,g,b or 108 | COLOUR OF r,g,b ON r,g,b (and likewise for GCOL) provide access to the 109 | full range of 16,777,216 colours. 110 | Custom screen modes can be used, via *NewMode, VDU23,22 or the newer forms 111 | of the MODE command. 112 | -------------------------------------------------------------------------------- /docs/compiling.txt: -------------------------------------------------------------------------------- 1 | These notes discuss how to compile the program under different operating 2 | systems. To make things simpler, there are batch files in the build 3 | directory for some common platforms - these can be run to automate the 4 | whole build. 5 | 6 | 7 | General 8 | ------- 9 | The program is written strictly in ANSI C. The upstream Brandy BASIC 10 | has been successfully compiled under the following operation systems: 11 | 12 | RISC OS Norcroft C 13 | NetBSD, FreeBSD gcc 14 | OpenBSD gcc 15 | Linux gcc 16 | Mac OS X Objective C 17 | Amiga SAS C 18 | DOS gcc, Jacob Navia's version of lcc and Borland C++ 19 | version 5.5. 20 | Windows gcc (mingw under Cygwin) 21 | 22 | It has also been compiled under Beos using gcc but this was just 23 | a test to make sure it worked. 24 | 25 | The Matrix Brandy fork is developed under Linux, and has been 26 | successfully compiled on: 27 | Linux 32-bit gcc 28 | Linux 64-bit gcc 29 | Windows 32-bit gcc (mingw under Cygwin) 30 | Windows 64-bit gcc (mingw under Cygwin) 31 | Mac OS X clang (using its gcc alias, with SDL 1.2 built from source of 32 | latest snapshot) 33 | Minix 3 clang (Text builds only) 34 | RISC OS Cross-compiled with gcc using gccsdk under Linux, and gcc 3.4 35 | within RISC OS. 36 | 37 | 38 | Hopefully the program will compile under other operating systems 39 | without any changes but it has only been tried on the above. 40 | 41 | The Linux version of the program is the main one. Earlier versions were 42 | largely developed under RISC OS except for the OS-specific parts. More 43 | recently the development focus has been for SDL under Linux. 44 | 45 | Under RISC OS, the source is found in the 'C' and 'H' 46 | subdirectories in the interpreter's directory in the normal way. 47 | Under the other operating systems it is kept in the 'src' 48 | subdirectory. 49 | 50 | As a general rule, the commands to compile the interpreter are: 51 | 52 | cd MatrixBrandy Change to the directory containing the 53 | interpreter. 54 | 55 | make recompiles modules 56 | 57 | Some defaults in Matrix Brandy can be overridden using the BRANDY_BUILD_FLAGS 58 | shell environment variable. Notable ones include: 59 | -DDEBUG Enable debugging options (and extended LISTO) 60 | -DBRANDY_STARTUP_MODE= Choose initial screen mode, default is 0 61 | -DBRANDY_DEFAULT_SIZE= Default amount of memory to allocate to 62 | BASIC workspace in kilobytes, default 1024. 63 | -DBRANDY_NODISPLAYOS Banner and *HELP don't show the running OS. 64 | -DBRANDY_BANNER_MINIMAL Show a minimal banner on startup: 65 | Matrix Brandy K 66 | 67 | BASIC 68 | 69 | >_ 70 | 71 | This works best with -DBRANDY_STARTUP_MODE=7 :) 72 | -DBRANDY_ALLOW_LOWERCASE_COMMANDS Allow immediate-mode commands to be 73 | entered in lower case. 74 | 75 | Compiling the graphical build (aside from RISC OS) requires SDL 1.2. 76 | 77 | On EL6, 7 and 8, and older Fedora, do: 78 | sudo yum install SDL-devel 79 | 80 | On EL9 and 10, do: 81 | sudo dnf config-manager --set-enabled crb 82 | sudo dnf install sdl12-compat-devel 83 | 84 | (EL is Red Hat Enterprise Linux, CentOS, AlmaLinux, Rocky Linux, 85 | Scientific Linux, Oracle Linux and any other Red Hat rebuild) 86 | 87 | On newer Fedora, certainly 38 and later: 88 | sudo dnf install sdl12-compat-devel 89 | 90 | For Debian-based distributions including RaspberryPiOS and Ubuntu, do: 91 | sudo apt-get install libsdl1.2-dev 92 | 93 | 94 | Compiling Under Different Operating Systems 95 | ------------------------------------------- 96 | Compilation of the OS-specific parts of the interpreter is 97 | controlled by a macro of the form: 98 | 99 | TARGET_xxxxxx 100 | 101 | where 'xxxxxx' is the target operating system, for example, 102 | TARGET_RISCOS and TARGET_LINUX. The macro is defined in 103 | target.h. The values for the various operating systems are 104 | as follows: 105 | 106 | RISC OS TARGET_RISCOS 107 | NetBSD TARGET_NETBSD 108 | OpenBSD TARGET_OPENBSD 109 | FreeBSD TARGET_FREEBSD 110 | Linux TARGET_LINUX 111 | Mac OS X TARGET_MACOSX 112 | DOS TARGET_DJGPP, TARGET_WIN32, TARGET_BCC32 113 | Amiga TARGET_AMIGA 114 | Beos TARGET_BEOS 115 | 116 | Which of the above to use is determined in target.h by checking 117 | the predefined macros that are supplied by the compiler, for 118 | example, under RISC OS, there is a macro __riscos and if this 119 | exists, the macro TARGET_RISCOS is defined. It will be necessary 120 | to find out what macros are predefined by the C compiler to be 121 | used to compile the interpreter. If it is gcc, the predefined 122 | macros can be found by looking at the 'specs' file. The command 123 | 'gcc -v' will say where this file is (if it exists). An 124 | alternative is to hard-code the TARGET_xxxx macro in target.h. 125 | 126 | 127 | target.h 128 | -------- 129 | The machine-specific options for compiling the program are defined 130 | in this include file. There is not much to set up and details of 131 | what is needed is given in the file. All of the conditional 132 | compilation in the program is controlled by what is set in 133 | target.h. 134 | 135 | 136 | Compiler Options 137 | ---------------- 138 | The options used for the non-debug version of the program have been 139 | found to give the best performance. They may not look the best and 140 | there may be cases where different options will give a better result 141 | for a particular Basic program but they seem to be good. 142 | 143 | 144 | RISC OS 145 | ------- 146 | The program has only been compiled with the Norcroft C compiler. 147 | 148 | Acorn's make utility is called 'amu', not 'make', and so the 149 | commands to compile the program are: 150 | 151 | amu 152 | - or - 153 | amu recompile 154 | - or - 155 | amu nodebug 156 | 157 | The program compiles and runs under RISC OS 3.1 or later. Note 158 | that the names of some of the source files are longer than ten 159 | characters, which might cause problems for users of versions 160 | of RISC OS earlier than 4.0. Either the names will have to be 161 | truncated or a filing system that supports longer names such as 162 | Richard Atterer's raFS will have to be used. 163 | 164 | 165 | *BSD and Linux 166 | -------------- 167 | There are no problems compiling the program under either of these 168 | operating systems. 169 | 170 | Linux and BSD targets implement graphics using the SDL libraries. 171 | Other targets can be made to support SDL by adding "#define USE_SDL" 172 | in the appropriate place in src/target.h. If graphics are not 173 | required, then see the "No Graphics" section of this file. 174 | 175 | 176 | DOS 177 | --- 178 | The program is meant to be compiled using D.J.Delorie's DOS 179 | extender DJGPP and the version of gcc that come with that but 180 | other compilers such as Borland's C++ compiler can be used. The 181 | file 'makefile' is set up for use with DJGPP and gcc but there 182 | are two others, 'makefile.bcc' for use with the Borland compiler 183 | and 'makefile.text' that creates a version of the interpreter that 184 | has no graphics support. 185 | 186 | 187 | No Graphics 188 | ----------- 189 | Some targets include graphics support by default: DOS implements 190 | graphics support using Jonathan Griffith's platform-idependent graphics 191 | library 'JLib', other targets implement graphics with SDL. 192 | 193 | If neither of these libraries are available then versions of the 194 | program that do not support graphics can be compiled by using the 195 | makefile 'makefile.text'. makefile.text compiles two different 196 | brandy executables: 197 | tbrandy: Text-only mode that supports ANSI escape sequences or 198 | the DOS conio library 199 | sbrandy: Simple text, output is restricted to functions such as 200 | printf() and putchar() 201 | 202 | The commands to compile the different versions of the program become: 203 | 204 | make -f makefile.text # to make sbrandy and tbrandy. 205 | make -f makefile.text sbrandy # to make sbrandy only. 206 | make -f makefile.text tbrandy # to make tbrandy only. 207 | 208 | make -f makefile.text recompile 209 | make -f makefile.text srecompile 210 | make -f makefile.text trecompile 211 | 212 | make -f makefile.text nodebug 213 | make -f makefile.text snodebug 214 | make -f makefile.text tnodebug 215 | 216 | depending on the version of the code wanted. 217 | 218 | Borland C++ 219 | ----------- 220 | The interpreter can be compiled using Borland's C compiler. The 221 | makefile to use is 'makefile.bcc'. This will only create an 222 | optimised version of the code, that is, it does not compile the 223 | debugging version. The only flavour of 'make' command that works 224 | is: 225 | 226 | make -f makefile.bcc 227 | --------------------------------------------------------------------------------