8-Bit Software Online Conversion
Decompression - Listing
10REM >LZSSD
20REM by Steven Flintham
30REM
40REM Version 1.00
50REM
60REM Tuesday 26th March 1996
70REM Wednesday 27th March 1996
80REM Wednesday 3rd April 1996
90REM Thursday 4th April 1996
100REM Monday 8th April 1996
110REM Wednesday 10th April 1996
120REM Saturday 13th April 1996
130:
140MODE 7
150PROCoff
160PROCinit1
170PROCload`mc
180PROCinit2
190PROCget`files
200PROCdecompress(input$,output$)
210IF FNanother GOTO 190
220VDU 22,7
230PROCenable
240END
250:
260DEF PROCinit1
270gf`status%=0
280ON ERROR PROCerror
290PROCdisable
300PROCtitle
310PRINT'"Please wait, initialising...
"
320use`file`buffer%=TRUE
330DIM block% 64
340IF use`file`buffer% THEN DIM file`b
uff% 512
350CLOSE #0
360ENDPROC
370:
380DEF PROCinit2
390DIM workspace% 4226:REM enough work
space for 12/7 decompression
400ENDPROC
410:
420DEF PROCerror
430IF gf`status%<>0 AND ERR>=128 THEN
REPORT:PRINT:GOTO 190
440VDU 22,7
450CLOSE #0
460PROCenable
470IF ERR<>17 THEN REPORT:PRINT " at l
ine ";ERL
480END
490:
500DEF PROCdisable
510*FX4,1
520ENDPROC
530:
540DEF PROCenable
550*FX4
560ENDPROC
570:
580DEF PROCoff
590VDU 23,1,0;0;0;0;
600ENDPROC
610:
620DEF PROCon
630VDU 23,1,1;0;0;0;
640ENDPROC
650:
660DEF PROCload`mc
670LOCAL fname$,in%,base%,apply%,diff%
,old%,new%,A%,X%,Y%
680IF use`file`buffer% THEN fname$="LZ
SSDFB" ELSE fname$="LZSSDFX"
690in%=OPENIN(fname$)
700IF in%=0 THEN PRINT'"Sorry, I can't
find ";fname$;"."':PROCenable:END
710DIM code% FNword(in%)
720?block%=in%
730block%!1=code%
740block%!5=FNword(in%)
750A%=4:X%=block% MOD 256:Y%=block% DI
V 256:CALL &FFD1
760base%=FNword(in%)
770FOR apply%=1 TO FNword(in%)
780diff%=FNword(in%)
790old%=code%?diff%+256*code%?(diff%+1
)
800new%=old%-base%+code%
810code%?diff%=new% MOD 256:code%?(dif
f%+1)=new% DIV 256
820NEXT
830CLOSE #in%
840in`file=&77
850out`file=&82
860buffer=&83
870buffer`size=&85
880break`even=&78
890offset`bits=&79
900length`bits=&7A
910out`size=&7F
920in`x=&8F
930in`y=code%+&1C0
940out`x=code%+&1C1
950out`y=code%+&1C2
960IF NOT use`file`buffer% THEN ENDPRO
C
970in`y=code%+&213
980out`x=code%+&214
990out`y=code%+&215
1000file`buffer=&8C
1010ENDPROC
1020:
1030DEF FNword(chan%)
1040=BGET #chan%+256*BGET #chan%
1050:
1060DEF PROCoscli($block%)
1070LOCAL X%,Y%
1080X%=block% MOD 256
1090Y%=block% DIV 256
1100CALL &FFF7
1110ENDPROC
1120:
1130DEF PROCtitle
1140CLS
1150PRINTTAB(7,0);CHR$141;CHR$132;CHR$1
57;CHR$135;"LZSS decompression ";CHR$15
6
1160PRINTTAB(7,1);CHR$141;CHR$132;CHR$1
57;CHR$135;"LZSS decompression ";CHR$15
6
1170PRINT CHR$131;"Version 1.00 (C) Ste
ven Flintham 1996"
1180ENDPROC
1190:
1200DEF PROCget`files
1210IF gf`status%=1 THEN GOTO 1270
1220IF gf`status%=2 THEN GOTO 1310
1230PROCtitle
1240VDU 28,0,24,39,4
1250PRINT "Whenever a filename is reque
sted you canalso enter a * command"
1260gf`status%=1
1270REPEAT
1280input$=FNfname`oscli("Input file: "
)
1290UNTIL FNvalid`input(input$)
1300gf`status%=2
1310REPEAT
1320output$=FNfname`oscli("Output file:
")
1330UNTIL FNvalid`output(output$)
1340gf`status%=0
1350VDU 26
1360ENDPROC
1370:
1380DEF FNfname`oscli(prompt$)
1390LOCAL fname$
1400REPEAT
1410PRINT'prompt$;
1420fname$=FNstrip`spaces(FNinput(1,255
,FALSE)):PRINT
1430IF LEFT$(fname$,1)="*" AND LEN(fnam
e$)<64 THEN PROCoscli(fname$)
1440UNTIL LEFT$(fname$,1)<>"*"
1450=fname$
1460:
1470DEF FNstrip`spaces(line$)
1480REPEAT
1490IF LEFT$(line$,1)=" " THEN line$=MI
D$(line$,2)
1500UNTIL LEFT$(line$,1)<>" "
1510=line$
1520:
1530DEF FNvalid`input(fname$)
1540LOCAL chan%,read`header%,version%
1550chan%=OPENIN(fname$)
1560IF chan%=0 THEN PRINT'"That file do
es not exist!":=FALSE
1570FOR read`header%=0 TO 4
1580block%?read`header%=BGET #chan%
1590NEXT
1600CLOSE #chan%
1610version%=block%?4:block%?4=13
1620IF $block%<>"LZSS" THEN PRINT'"That
is not an LZSS file!":=FALSE
1630IF version%<>0 THEN PRINT'"That is
not a version 0 LZSS file!":=FALSE
1640=TRUE
1650:
1660DEF FNvalid`output(output$)
1670LOCAL chan%
1680chan%=OPENIN(output$)
1690IF chan%=0 THEN =TRUE
1700CLOSE #chan%
1710PRINT'"That file already exists. Ar
e you sure you want to overwrite it? (Y
/N) ";
1720IF NOT FNyes THEN PRINT "No":=FALSE
1730PRINT "Yes"
1740REM Use OPENOUT to check for write-
only errors
1750chan%=OPENOUT(output$):CLOSE #chan%
1760=TRUE
1770:
1780DEF PROCdecompress(input$,output$)
1790LOCAL in%,buffer`size%,time%,input`
size%,output`size%,hr%,min%,sec%,load%,e
xec%,A%,X%,Y%
1800PROCtitle
1810PRINT'"Input file: ";CHR$131;RIGHT$
(input$,27)
1820PRINT "Output file:";CHR$131;RIGHT$
(output$,27)
1830in%=OPENIN(input$):?in`file=in%
1840PTR #in%=5:?offset`bits=BGET #in%:?
length`bits=BGET #in%
1850PRINT "Offset bits:";CHR$131;?offse
t`bits
1860PRINT "Length bits:";CHR$131;?lengt
h`bits
1870PRINT'"Please wait, decompressing..
."
1880PRINT'"Bytes read: ";CHR$131;"&";
:?in`x=POS:?in`y=VPOS:PRINT "000000"
1890PRINT "Bytes written:";CHR$131;"&";
:?out`x=POS:?out`y=VPOS:PRINT "000000";
1900PTR #in%=8:FOR read%=0 TO 3:out`siz
e?read%=BGET #in%:NEXT
1910FOR read%=0 TO 7:block%?read%=BGET
#in%:NEXT
1920load%=!block%:exec%=block%!4
1930?break`even=(1+?offset`bits+?length
`bits) DIV 9
1940?buffer=workspace% MOD 256:buffer?1
=workspace% DIV 256
1950buffer`size%=2^?offset`bits+?break`
even+2^?length`bits
1960?buffer`size=buffer`size% MOD 256:b
uffer`size?1=buffer`size% DIV 256
1970IF use`file`buffer% THEN ?file`buff
er=file`buff% MOD 256:file`buffer?1=file
`buff% DIV 256
1980?out`file=OPENOUT(output$)
1990PTR #in%=24
2000time%=TIME
2010CALL code%
2020time%=TIME-time%
2030IF time%=0 THEN time%=1:REM avoid m
inute risk of division by zero
2040input`size%=PTR #in%:REM includes h
eader size
2050output`size%=PTR #?out`file
2060PRINTTAB(?in`x,?in`y);RIGHT$("00000
0"+STR$÷input`size%,6)
2070PRINTTAB(?out`x,?out`y);RIGHT$("000
000"+STR$÷output`size%,6)
2080hr%=time% DIV 360000
2090min%=(time%-hr%*360000) DIV 6000
2100sec%=(time%-hr%*360000-min%*6000) D
IV 100
2110PRINT'"Time taken: ";CHR$131
;hr%;":";RIGHT$("00"+STR$(min%),2);":";R
IGHT$("00"+STR$(sec%),2)
2120PRINT "Speed: ";CHR$131
;(100*input`size%) DIV time%;" bytes/sec
ond"
2130PRINT "Input/output ratio:";CHR$131
;input`size%*100 DIV output`size%;"%"
2140CLOSE #in%
2150CLOSE #?out`file
2160$workspace%=output$
2170block%!0=workspace%
2180block%!2=load%
2190block%!6=exec%
2200X%=block% MOD 256:Y%=block% DIV 256
2210A%=2:CALL &FFDD
2220A%=3:CALL &FFDD
2230ENDPROC
2240:
2250DEF FNanother
2260PRINT'"Decompress another file? (Y/
N)";
2270=FNyes
2280:
2290DEF FNyes
2300LOCAL key$
2310*FX21
2320REPEAT
2330key$=CHR$(GET AND &DF)
2340UNTIL key$="Y" OR key$="N"
2350=(key$="Y")
2360:
2370DEF FNinput(min%,max%,numeric%)
2380LOCAL input$,key$
2390input$=""
2400*FX21
2410PROCon
2420REPEAT
2430REPEAT
2440key$=GET$
2450UNTIL (key$>="0" AND key$<="9") OR
(NOT numeric% AND key$>=" " AND key$<="÷
") OR key$=CHR$13 OR key$=CHR$127
2460IF key$<>CHR$13 AND key$<>CHR$127 A
ND LEN(input$)<max% THEN input$=input$+k
ey$:PRINT key$;
2470IF key$=CHR$127 AND input$<>"" THEN
input$=LEFT$(input$,LEN(input$)-1):VDU
127
2480UNTIL LEN(input$)>=min% AND LEN(inp
ut$)<=max% AND key$=CHR$13
2490PROCoff
2500=input$