Welcome, Guest
You have to register before you can post on our site.

Username
  

Password
  





Search Forums

(Advanced Search)

Forum Statistics
» Members: 264
» Latest member: zaashleysasdoz390
» Forum threads: 1,074
» Forum posts: 6,439

Full Statistics

Online Users
There are currently 337 online users.
» 0 Member(s) | 335 Guest(s)
Bing, Google

Latest Threads
Printing with FZX
Forum: Help & Support
Last Post: boriel
07-17-2025, 09:08 PM
» Replies: 1
» Views: 255
Strange Happenings
Forum: Bug Reports
Last Post: boriel
05-23-2025, 09:15 AM
» Replies: 4
» Views: 2,344
.tap file code not execut...
Forum: Help & Support
Last Post: Zoran
04-28-2025, 10:59 AM
» Replies: 4
» Views: 2,589
Exit from more than one l...
Forum: Wishlist
Last Post: Duefectu
04-23-2025, 10:06 PM
» Replies: 3
» Views: 2,177
put small ASM programs li...
Forum: How-To & Tutorials
Last Post: Zoran
04-18-2025, 02:02 PM
» Replies: 6
» Views: 5,049
Creating +3 Menus - Loadi...
Forum: Help & Support
Last Post: merlinkv
04-16-2025, 02:08 PM
» Replies: 6
» Views: 3,565
Randomize not very random...
Forum: Help & Support
Last Post: Zoran
04-08-2025, 10:40 AM
» Replies: 4
» Views: 3,284
Scope rules
Forum: Bug Reports
Last Post: Zoran
04-04-2025, 09:46 AM
» Replies: 2
» Views: 1,840
Using constants not allow...
Forum: Bug Reports
Last Post: baltasarq
03-19-2025, 10:00 PM
» Replies: 8
» Views: 4,464
404 page not found
Forum: Documentation
Last Post: boriel
03-08-2025, 07:16 PM
» Replies: 5
» Views: 5,281

 
  Optimisation level 3 Bug (*solved*)
Posted by: LCD - 04-10-2009, 06:22 PM - Forum: Bug Reports - Replies (5)

Hi Boriel,

I wrote the following little game (which is supposed to become a "Jewel Quest" clone one day :-):

Code:
dim a as uinteger
dim x as ubyte
dim y as ubyte
dim solv as ubyte
dim posx as uinteger
dim posy as uinteger


sub field(x as uinteger,y as uinteger,obj as ubyte)
  dim adr as uinteger
  dim adr1 as uinteger
  dim col as ubyte
  adr=22528+x*3+y*96
  adr1=50064+x+y*8
  col=56
  if obj=0 then col=2:end if
  if obj=1 then col=3:end if
  if obj=2 then col=4:end if
  if obj=3 then col=5:end if
  if obj=4 then col=6:end if
  if obj=5 then col=7:end if
  if obj=64 then col=48:end if
  if peek adr1 then col=col+8:end if
  poke adr,col:poke adr+1,col:poke adr+2,col
  poke adr+32,col:poke adr+33,col:poke adr+34,col
  poke adr+64,col:poke adr+65,col:poke adr+66,col
end sub
sub DisplayField()
  adr=50000
  for y=0 to 7
    for x=0 to 7
      a=peek(adr)
      adr=adr+1
      field(x,y,a)
    next x
  next y
end sub
sub ClearField(x as uinteger,y as uinteger)
  poke 50000+x+y*8,64
  poke 50064+x+y*8,1
end sub

function GetFieldObj(x as uinteger,y as uinteger) as ubyte
  return peek (50000+x+y*8)
end function
sub SetFieldObj(x as uinteger,y as uinteger,obj as ubyte)
  poke 50000+x+y*8,obj
end sub

function CheckBoard(x as integer,y as integer)
  solved=0
  dim current as ubyte
  dim c1 as ubyte
  dim c2 as ubyte
  current=GetFieldObj(x,y)
  c1=GetFieldObj(x-1,y)
  c2=GetFieldObj(x-2,y)
  if x>3 then
    if c1=current and c2=current and GetFieldObj(x-3,y)=current and GetFieldObj(x-4,y)=current then for a=0 to 4:ClearField(x-a,y):next a:solved=solved+1:end if
  end if
  if x>2 then
    if c1=current and c2=current and GetFieldObj(x-3,y)=current then for a=0 to 3:ClearField(x-a,y):next a:solved=solved+1:end if
  end if
  if x>1 then
    if c1=current and c2=current then for a=0 to 2:ClearField(x-a,y):solved=solved+1:next a:end if
  end if
  c1=GetFieldObj(x,y-1)
  c2=GetFieldObj(x,y-2)
  if y>3 then
    if c1=current and c2=current and GetFieldObj(x,y-3)=current and GetFieldObj(x,y-4)=current then for a=0 to 4:ClearField(x,y-a):next a:solved=solved+1:end if
  end if
  if y>2 then
    if c1=current and c2=current and GetFieldObj(x,y-3)=current then for a=0 to 3:ClearField(x,y-a):next a:solved=solved+1:end if
  end if
  if y>1 then
    if c1=current and c2=current then for a=0 to 2:ClearField(x,y-a):solved=solved+1:next a:end if
  end if
  return solved
end function
sub fieldupdate()
  for x=0 to 7
    for y=0 to 7
      if GetFieldObj(x,y)=64 then
        ypos=y
        while ypos>0
          SetFieldObj(x,ypos,GetFieldObj(x,ypos-1))
          ypos=ypos-1
        end while
        SetFieldObj(x,0,rnd*5)
      end if
    next y
  next x
end sub
function SolveField() as ubyte
  solv=0
  for y=0 to 7
    for x=0 to 7
      solv=solv+CheckBoard(x,y)
    next x
  next y
  return solv
end function
sub PutCoin(x as uinteger,y as uinteger)
  print at y,x;"\  \..\  "
  print at y+1,x;"\ :\::\: "
  print at y+2,x;"\  \''\  "
end sub

sub DisplayCursor(x as integer,y as integer,mode as byte)
  dim adr as uinteger
  dim newcol as ubyte
  adr=22528+x*3+y*96
  poke 65535,peek adr
  asm
    ld a,(65535)
    and 7
    ld (65535),a
  end asm
  if mode then
    poke 65535,(peek 65535)+56
  else
    adr1=50064+x+y*8
    if peek adr1 then
      poke 65535,peek 65535+8
    end if
  end if
  newcol=peek 65535
  poke adr,newcol
  poke adr+1,newcol
  poke adr+2,newcol
  poke adr+32,newcol
  poke adr+33,newcol
  poke adr+34,newcol
  poke adr+64,newcol
  poke adr+65,newcol
  poke adr+66,newcol
end sub






randomize

for a=0 to 63
  poke 50000+a,rnd*5
  poke 50064+a,0
next a
asm
  ld hl,50000
  ld de,50128
  ld bc,64
  ldir
end asm

paper 0:ink 7:border 0:cls
'poke 23607,127
'poke 23606,16

print at 2,0;"Controls"
print at 4,0;"1) Keyboard"
print at 5,0;"2) Sinclair Joystick"

controls1:
if inkey$="1" then
  up$="q"
  dw$="a"
  le$="o"
  ri$="p"
  fi$="m"
  goto controls2
end if
if inkey$="2" then
  up$="9"
  dw$="8"
  le$="6"
  ri$="7"
  fi$="0"
  goto controls2
end if
goto controls1
controls2:
cls



for y=0 to 7
  for x=0 to 7
    PutCoin(x*3,y*3)
  next x
next y
posx=4
posy=4

solveboard:
  solv=SolveField()
  DisplayField()
  fieldupdate()
  if solv then goto solveboard:end if
controlloop0:
DisplayCursor(posx,posy,1)
for a=0 to 5:pause 1:next a
controlloop1:

if inkey$=up$ and posy>0 then DisplayCursor(posx,posy,0):posy=posy-1:DisplayCursor(posx,posy,1):goto controlloop0:end if
if inkey$=dw$ and posy<7 then DisplayCursor(posx,posy,0):posy=posy+1:DisplayCursor(posx,posy,1):goto controlloop0:end if
if inkey$=le$ and posx>0 then DisplayCursor(posx,posy,0):posx=posx-1:DisplayCursor(posx,posy,1):goto controlloop0:end if
if inkey$=ri$ and posx<7 then DisplayCursor(posx,posy,0):posx=posx+1:DisplayCursor(posx,posy,1):goto controlloop0:end if
if inkey$=fi$ then gosub activate:end if

goto controlloop1
activate:
  asm
    ld hl,50000
    ld de,50128
    ld bc,64
    ldir
  end asm
  if inkey$=up$ and posy>0 then
    adr=50000+posx+posy*8
    a=peek adr
    b=peek (adr-8)
    poke adr,b
    poke adr-8,a
    gosub check
    return
  end if
  if inkey$=dw$ and posy<7 then
    adr=50000+posx+posy*8
    a=peek adr
    b=peek (adr+8)
    poke adr,b
    poke adr+8,a
    gosub check
    return
  end if
  if inkey$=le$ and posx>0 then
    adr=50000+posx+posy*8
    a=peek adr
    b=peek (adr-1)
    poke adr,b
    poke adr-1,a
    gosub check
    return
  end if
  if inkey$=ri$ and posx>0 then
    adr=50000+posx+posy*8
    a=peek adr
    b=peek (adr+1)
    poke adr,b
    poke adr+1,a
    gosub check
    return
  end if

  complete=0
  for a=0 to 63
    if peek(50064+a) then complete=complete+1:end if
  next a
  if complete=64 then
    goto won
  end if

goto activate
check:
  solv=SolveField()
  if solv then
    DisplayField()
    goto solveboard
  else
    asm
      ld hl,50128
      ld de,50000
      ld bc,64
      ldir
    end asm
    goto controlloop0
  end if
  return

won:
cls
print "Congratulations"

The Problem is:
It works with Optimisation Level 2, but on Optimisation level 3 it throws "Unexpected tokem IX [IX] at line 1208"

Print this item

  Version 1.1.4 released!
Posted by: boriel - 03-30-2009, 06:46 AM - Forum: ZX Basic Compiler - No Replies

Changes from Version 1.1.2 to 1.1.4

  • + The peephole optimizer has been enabled and seems to be working
    reasonabily well (use -O3 for higher optimization).
  • ! When a DIV BY ZERO error occurs with floating point numbers the program
    crashes and resets the computer. This behaviour has been fixed
    and now returns 0 value and sets the error code 6 (Numbert Too big)
    in the ERR_NR system variable.
  • * Refactorization of the assembler and compiler so they now
    shared the OPTIONS in a better way (still to be finished). This
    makes easier to program future compiler options. Now also --debug
    flag is additive, showing more verbosity the more it is used.
  • + Memory optimization: The PRINT routine (which is about 1K) is not
    included if not USED.
  • ! Fixed a bug in negative constant integer typecasting (Thanks to LCD
    at WOS for reporting it! ;-)). It was causing decremental FOR..NEXT
    to fail.
  • ! Scientific notation numbers (e.g. 2e10) were not correctly parsed.
    Fixed. Thanks again to LCD. ;-)
  • + Added TAB compatibility for the PRINT command (both as a command
    and as a CHR$ control character).
  • * PRINT code optimized for size, maintaining speed.

====
TODO:
  • Some little more peephole optimizations.
  • Implementation of SAVE/LOAD/VERIFY with DATA/CODE/SCREENS (And maybe even the BASIC zone)
  • 8 bits AND/OR/NOT/XOR instructions
  • READ/DATA/RESTORE (mostly for compatibility)
  • CLEAR for filling memory zones.
  • USR n and USR n$ function (mostly for compatibilty)

Print this item

  Version 1.1.1 released!
Posted by: boriel - 03-16-2009, 08:10 AM - Forum: ZX Basic Compiler - No Replies

This version fixed some issues and introduces interesting improvements:

Changes from Version 1.1.0 to 1.1.1

  • !Fixed a bug in CONTINUE DO which was not being correctly compiled
  • +PRINT routines were included even when neither PRINT nor
    drawing primitives were used. Optimized.[/*]
  • ! Fixed a lot of syntax error checkings with array operations.
  • ! Fixed array dimension checking
  • + Expanded syntax: Direct array assignation a = b (being a and b
    arrays of thes same type an size)[/*]
  • ! Fixes an error exception on syntax error for array subscripting.
  • * Changed alloc functions to match the FreeBasic names.
  • * Using a wrong sigil in array declaration is now forbidden.
  • * Better sigils (suffixes) types managements at DIM declarations.
  • * Lot of internal source code refactoring
  • + DIM r AT @a(k0, k1, ...) is allowed (k0, k1, ... constants)
  • ! Fixed a bug for local variables and parameters when the offset is
    very large (> 128)
  • + Enabled the --sinclair flag for automatic sinclair libraries inclusion
  • + Added SetAttr routine whichs changes the attribute of
    screen coordinate (I, J) with the given color attr
    value.
  • ! Fixed a buggy modu16 modi16 implementation that was not compiling
    correctly
  • * Output asm code is now slightly optimized (for speed an memory)
  • ! Fixed a bug in intenger parameters (16 and 32 bits)
  • ! Fixed a compiler crash when using arrays of Fixed Point numbers

Print this item

  Negative STEP does not work (*solved*)
Posted by: LCD - 03-15-2009, 07:03 PM - Forum: Bug Reports - Replies (12)

Hi Boriel, I just trying to write some stuff in ZX Basic compiler 1.1.0, but I ran into some problems:

Code:
x=0
if x=1 then
  print "1"
else if x=0 then
  print "0"
end if

I got the message "Unexpected end of file", so if it is a part of FOR NEXT Loop, I got the message "Unexpected Token 'NEXT' <NEXT>". ELSE alone works, but I was sure, ELSE IF should work too, Or maybe I'm wrong?

Another one: the program does not accept Exponents: 2e4 (=2000) or similar.
And finally:
Negative STEP does not work with integers or long, only with floats or byte:
Code:
dim x as integer

for x=7 to 1 step -1
  print x
next x

The compiler is otherwise fantastic! Please continue your great work!

Print this item

  Version 1.1.0 released!
Posted by: boriel - 03-11-2009, 08:35 AM - Forum: ZX Basic Compiler - No Replies

This version fixed some issues and introduces interesting improvements:

Changes from Version 1.0.9 to 1.1.0

  • SCREEN$ coordinated were swapped. Fixed.
  • DIM .. AT was not correctly working with local vars nor params. Fixed.
  • Added BOLD "attribute".
    Code:
    PRINT BOLD 1; "Hello"
  • Added ITALIC "attribute".
    Code:
    PRINT ITALIC 1; "Hello"
  • Added malloc, free and realloc functions to work with the heap
  • Some code rearrangement
  • The IFDEF directive was not working in the preprocessor. Fixed.
================================================================
Changes from Version 1.0.8 to 1.0.9
  • Fixed a bug which could crash the program if no memory
  • Added better error handler for parameter declaration
  • Added UCase function
  • Added Lcase and fixed ucase to be case insensitive
  • Added MultiKeys Function (similar to FREEBASIC) so multiple keys can be checked at once
  • Added GetKeyScanCodes
  • Added HEX and HEX16 functions to return HEXadecimal string representation of numbers
  • Fixed a bug when a$(n TO) was specified
  • Optimization: Remove unnecessary jumps at function returns.
  • STORE16 now generates a more efficient backend (Z80 ASM) code.
  • Added alias for arrays. Now you can declare:
    Code:
    DIM a(10)
      DIM c at @a
  • Better code generation for STORE32 and STOREF backend
  • Optimized constant array assignation as a direct store.
  • Added constant array Read access optimizations

Print this item

  Version 1.0.8 released!
Posted by: boriel - 03-01-2009, 12:34 AM - Forum: ZX Basic Compiler - No Replies

This release includes new fixes and improvements:

  • Fixed a bug in the PRINT command when printing floating point numbers due to a Spectrum ROM Bug. The temporary attributer were not being used.
  • Fixed a bug in the STR$ function that made the program to freeze and also clears the temporary attributes (related to the ROM bug as above).
  • Fixed a bug in the assembler which, sometimes won't assemble if #init directives were used. Also some code clean up.
  • Now you can enter ink/paper codes and graphic characters ala BASIN (read below)
  • Added shift bit instructions (SHL, SHR)
About the spectrum ROM bug. The original STR$ Basic function clean up the temporary attributes. Try this in your ZX Spectrum:
Code:
10 PRINT PAPER 2; STR$(0)
The bug causes that PAPER 2 has no effect (you should see a "0" over a red background). ZX Basic workaround this bug now.

To enter an UDG character like "A" type \A. For example:
Code:
PRINT "\a": REM This will print UDG "A"
The numeric graphics characters can be obtained using the backslash (as above) followed by two punctuation characters. These ones are: [ ] ['] [:] and [.] characters. Each dot represents a square in the graphic character. Try this:
Code:
10 PRINT "\  \::\:'\:.\..\'."

Print this item

  Version 1.0.7 released!
Posted by: boriel - 02-22-2009, 10:58 AM - Forum: ZX Basic Compiler - No Replies

This release includes new fixes and improvements:

  • Fixes a bug in the DRAW command. The draw implementation was buggy. The new DRAW implementation works ok, and is faster and smaller.
  • Support for DRAW with 3 arguments. Now you can DRAW arcs as in Sinclair BASIC. The routine works exactly as the ZX Spectrum ROM, but also allows drawing in the lower 16 scan lines
  • Optimization: If a function is not called, and you use -O1 (or a higher number), it won't be compiled, allowing saving space
  • Optimization: If a global variable is not used, and you use -O2 (or a higher number), it won't be compiled, allowing saving space
  • Optimization: The code generated for temporary atributes is now smaller and faster
New compiler options:
  • Use --array-base=1 to start arrays at subscript 1 (default is 0)
  • Use -On to enable optimizations. Higher n number leads to higher optimizations

Print this item

  About constants
Posted by: LCD - 02-13-2009, 06:10 PM - Forum: ZX Basic Compiler - Replies (9)

Defining constants with CONST Constant as UByte=0 is not the ideal way, because they can be easy mistaken for variables, and can interfer with variables. So my proposal is to change it to similar way, PureBasic does:
#Constant as UByte=0, and all constants are marked with "#" sign in the front. In PureBasic it is a little different, as the constant and variable types are defined this way: #constant.ub=0 (ub=short for unsigned byte, has to be defined only one time).
apart from this I propose to include build-in constants with ROM Labels and System variables:
#KSTATE=23552, #LASTK=23560, #REPDEL=23561, #REPPER=23562, ...
#start=$0, #error_1=$8, #print_a_1=$10, #get_char=$18
#test_char=$1C, #next_char=$20, #fp_calc=$28, #bc_spaces=$30, ...
Also constants for some other usages:
#False=0, #True=1, #Zero=0
#Black=0, #Blue=1, #Red=2, #Magenta=3,...

Is this a good idea???

Print this item

  Online Documentation (Wiki)
Posted by: boriel - 02-13-2009, 03:31 PM - Forum: Documentation - No Replies

There is (already) a Wiki with the online documentation.

Some users are unaware of this documentation. Please, read there before asking for help since the documentation includes a programming reference and lot of examples, code snippets, etc.

Note: To contribute to the wiki you must register (create an account) in this forum, and later login into the wiki with the same user/pass.

Print this item

  Version 1.0.5 released!
Posted by: boriel - 02-13-2009, 08:33 AM - Forum: ZX Basic Compiler - No Replies

New version 1.0.5 released.

This version fixes very important bugs. Please download this version before reporting problems with the compiler.

Print this item