CPCWiki forum

General Category => Programming => Topic started by: tastefulmrship on 12:44, 28 September 11

Title: Dumb question #15839 - BITBUSTER 1.2
Post by: tastefulmrship on 12:44, 28 September 11
Hi all!  :-[
Please forgive even more of my petty ignorance!

I've been trying to get my head around this for a while now and I have to give up and admit I need help... again!

When I add some .pck files (created with BITBuster 1.2 on a PC) to my .dsk in WinAPE 2A18 they come up as Unknown ASCII/Binary files and, therefore, refuse to load directly into CPC memory; is there an easy way to get these files to show as Binary?

Thanks again,
- JTMS...
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: redbox on 12:48, 28 September 11
Have you ticked the 'Add/Remove AMSDOS headers' option in the WinAPE Disc Editor before you copy the file into the DSK from your PC...?
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: tastefulmrship on 13:07, 28 September 11
Quote from: redbox on 12:48, 28 September 11
Have you ticked the 'Add/Remove AMSDOS headers' option in the WinAPE Disc Editor before you copy the file into the DSK from your PC...?
Ah ha! Top stuff!! Thank you!
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: redbox on 13:10, 28 September 11
Quote from: tastefulmrship on 13:07, 28 September 11
Ah ha! Top stuff!! Thank you!


Np - I make that mistake all the time  :)


Funny to see we're both playing with crunchers today.


Do you have a link to the Bit Buster PC program and CPC decruncher routine?
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: tastefulmrship on 13:14, 28 September 11
Quote from: redbox on 13:10, 28 September 11
Do you have a link to the Bit Buster PC program and CPC decruncher routine?
Here is the one I'm using at the moment; http://cpcrulez.fr/applications_tools_cruncher_bitbuster_Z80.htm (http://cpcrulez.fr/applications_tools_cruncher_bitbuster_Z80.htm)

However, I'm finding that I cannot resolve back to BASIC (or any other MC routine)... it must be something I've done.
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: redbox on 13:24, 28 September 11
Quote from: tastefulmrship on 13:14, 28 September 11
However, I'm finding that I cannot resolve back to BASIC (or any other MC routine)... it must be something I've done.


Well if you want to use it under BASIC it says in the source "You must save secondary registers if you want to use the routine under Basic." - but calling routine main (at beginning, being &A000) does this for you.  Of course you'll need to change the source (set to &4000) and destination (set to &C000) in main to where your code is and you want it to be depacked to before you compile the binary.


If you want to use it in MC, then just LD HL,source:LD DE,destination and CALL depack.  Assume most registers are destroyed I expect.


It does pack quite nicely, but not quite as well as Exomizer though.
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: redbox on 13:38, 28 September 11
Er, yeah.


Caught in an infinite loop it appears...


Use exomizer  8)
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: tastefulmrship on 13:40, 28 September 11
The problem was the source files still had AMSDOS headers... and BITBuster doesn't really like AMSDOS headers!
I re-packed the headerless files and all is fine!

I've had differing results with all crossdev packers; there doesn't seem to be a 'best of', as it depends on the source file itself as to which packer results in the smallest file. Sometimes PUCruncher is better, sometimes Exomiser and so on. It's personal taste, I guess. BITBuster does the job perfectly for me.


EDIT:
Quote from: redbox on 13:38, 28 September 11
Er, yeah.
Caught in an infinite loop it appears...
Use exomizer  8)
Use headerless source files! Tick that AMSDOS header button before copying to PC.
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: redbox on 14:00, 28 September 11
Quote from: tastefulmrship on 13:40, 28 September 11
The problem was the source files still had AMSDOS headers... and BITBuster doesn't really like AMSDOS headers!


Hahahahaha, that's funny considering how the thread started!  Nice find though.

Quote from: tastefulmrship on 13:40, 28 September 11
I've had differing results with all crossdev packers; there doesn't seem to be a 'best of', as it depends on the source file itself as to which packer results in the smallest file. Sometimes PUCruncher is better, sometimes Exomiser and so on. It's personal taste, I guess. BITBuster does the job perfectly for me.


I agree, depends on the situation.  And exomizer requires a buffer which some others don't.


I'm writing some new software with lots of crunchers in though, so I'll include PUCrunch and BitBuster now.
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: TFM on 16:35, 28 September 11
Have you ever compared CPCT aginst PC crunchers? My experiences with CPCT are very good. Thank's Madram!
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: Nich on 11:45, 09 October 11
Quote from: TFM/FS on 16:35, 28 September 11
Have you ever compared CPCT aginst PC crunchers? My experiences with CPCT are very good. Thank's Madram!

In my opinion, CPCT is one of the best native CPC crunchers, but compression is very slow indeed, even on a CPC emulator with the speed set to maximum. The likes of Exomizer and MegaLZ offer much better compression than CPCT and have the advantage of very fast compression - but on the other hand, CPCT's decompression routines are much faster than Exomizer and MegaLZ.

I really ought to write a CPCWiki article on how to use Exomizer with a CPC... ::)
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: TFM on 21:17, 09 October 11
An article would be great!

How much better is exomizer compared to CPCT when looking at file-size?

Excuse my words, but I don't even give a crap on compression time. That's what I do once in a lifetime for a a given version of a program. So I can wait that minute (especially when using an emulator).

But what really matters is (aside of the size of the compressed file) the DEcompression time, because I will have to wait for the decompression every time I want to use the program. And if CPCT is better there (wow!). Unexpected, but that kick's PC-butts ;-)

However, if the filesize of a exomizer-compressed file is way better that other crunchers, that I wouldn't mind to wait 2 seconds longer for decompression. However a difference between 12 KB and 15 Kb wouldn't be an argmument for me.

I don't have exomizer, bitbuster and all that stuff, but it would be interesting to have some tables to compare their compression rate :-)

Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: redbox on 21:34, 09 October 11
Quote from: TFM/FS on 21:17, 09 October 11
An article would be great!

Agreed.  Something to remember when using Exomizer is that the input has to be in lowercase, and not uppercase as shown in all the documentation.  So for example, the correct way to use it on your PC is:


exomizer raw filename.bin


and not


EXOMIZER RAW FILENAME.BIN


Took me a while to work out why it wasn't working when I was using it  ;)

Quote from: TFM/FS on 21:17, 09 October 11
I don't have exomizer, bitbuster and all that stuff, but it would be interesting to have some tables to compare their compression rate :-)

See here for a comparison: http://cpcrulez.fr/applications_tools_cruncher_COMPARATIF.htm (http://cpcrulez.fr/applications_tools_cruncher_COMPARATIF.htm)
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: TFM on 21:38, 09 October 11
Yes, thank's I saw that before, but ... it's French!  :-X
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: redbox on 21:41, 09 October 11
Ich finde deutschen einfacher als franzosisch, es ist wahr...

Aber franzosisch ist wirklich nicht zu hart TFM!


Original        &7025
CPC_T v3.0 Beta 1    &35D4
Exomizer v2.0 beta 6    &2AD5
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: TFM on 21:46, 09 October 11
French and Spanish are the most beautiful languages in the world.

To learn German must be a pain in the arse back. However even I can do a bit in English, and if I wouldn't have that pain in the head (no I had no alcolhol for 5 weeks!), I probably would get along with French better.
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: redbox on 21:53, 09 October 11
I found German much easier than French.  German generally sticks to the rules, French just breaks them all the time.

Exomizer does crunch an amazing amount, but I have heard of problems with decompression sometimes.  It has been used a lot though, Fano uses it in the new R-Type and Axelay mentions using it a lot.  SyX talked to me about compressors and he has found mixed results too.

But, as you say, it is all down to personal choice and thankfully there are a lot of options so you can see which one fits best in each situation.  Like you say, it's not always about the compression but sometimes about how fast decompression is etc.

Rather than a Wiki article about just Exomizer, it would be nice to see one about Crunchers in general which weighs up the pros and cons of each one.
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: SyX on 18:26, 10 October 11
Apropos of compressor (the Babel subject is other world, jejejeje, and wait to add the dialects to the discussion ;) ), i don't trust in exomizer, i have used in a few projects without problems even in backward mode, but i have crunched a few files that the z80 decruncher can not decrunch and passed a lot of time debugging my code :-[

Because that, now i use aplib exclusively, the decruncher is short (only 163 bytes, while exomizer are 191 bytes + 156 bytes for the table  exo_mapbasebits) and noticebly faster than exomizer, but exomizer crunch better.

Another great thing with aplib is that i can decrunch in place easily, loading the file at the end of destination ram zone with only a clearance of 16 bytes (SOURCE_ADDRESS + LEN_DECRUNCH_FILE - LEN_CRUNCH_FILE + 16), normally is 3 ó 4 bytes, but with 16 i'm completely sure :) Although i would like it was possible to decrunch through $FFFF, because in Renegade i have a hollow of a few hundreds of bytes where put my code in $8000, and i would be nice make a big file from $8200 - $8000, instead of making two files ($0000-$8000 / $8200-$FFFF).

I have studied a few Z80 decrunchers from zx, msx, master system, gb, ... and a few 68000 decrunchers, i have converted packfire (http://www.pouet.net/prod.php?which=54840) tiny mode to z80, and how aplib, it doesn't need a buffer in ram how exomizer (the table is in the first 26 bytes of every crunched file) and the decrunched files are the same size that exomizer (or even a few bytes smaller),  but is much much more slower and the tiny mode only can compress up 32 KBs, not a single byte more.

I have used the table and files that appears in MegaLZ Benchmarks (http://lvd.nm.ru/MegaLZ/) and i have updated with these 3 compressors, plus ZIP and 7Z to compare them with modern compressors.(*) Table update in my next post

And i'm going to attach my packfire tiny decruncher, feel free to optimize, it's so slowwwwww  :P ; ---------------------------------------------------------------------------
; Packfire tiny decruncher for Z80 by Syx 2011
; Original MC68000 code by Franck "hitchhikr" Charlet
; ---------------------------------------------------------------------------

; ---------------------------------------------------------------------------
; packfire_decrunch: HL = Source / DE = Destination
; ---------------------------------------------------------------------------
packfire_decrunch
    PUSH HL
    POP  IX                     ; IX = tabla de frecuencias
    LD   BC,26
    ADD  HL,BC                  ; HL = Crunch data
    LD   A,(HL)                 ; Initilize bit counter (A)
    INC  HL
literal_copy
    LDI
main_loop
    CALL get_bit
    JR   C,literal_copy
    LD   IYL,$FF
get_index
    INC  IYL
    CALL get_bit
    JR   NC,get_index

    EX   AF,AF'
    LD   A,IYL
    CP   $10
    RET  Z                      ; Decrunch finish
    EX   AF,AF'

    CALL get_pair               ; Before the CALL IY < 256 always, after return can be IY > 255
    LD   (sm_len + 1),IY        ; Bytes to copy *** IY > 255 ***

    EX   AF,AF'
    LD   A,IYL
    CP   3
    JR   NC,es_mayor_2
    DEC  A
    JR   Z,es_1
    DEC  A
    JR   NZ,es_0
es_2
    LD   A,$04                  ; table_len[2]
    LD   BC,$0020               ; table_dist[2]
    JR   fin_cmp
es_1
    LD   A,$02                  ; table_len[1]
    LD   BC,$0030               ; table_dist[1]
    JR   fin_cmp
es_0
es_mayor_2
    LD   A,$04                  ; table_len[0]
    LD   BC,$0010               ; table_dist[0]
fin_cmp
    LD   (sm_d0 + 1),BC
    LD   B,A
    EX   AF,AF'

    CALL get_bits
    CALL get_pair

    PUSH HL
    LD   H,D
    LD   L,E                    ; A3 = A1
    LD   B,IYH
    LD   C,IYL                  ; BC = D3
    OR   A                      ; Clear Carry
    SBC  HL,BC
sm_len
    LD   BC,$0000               ; Can be > 255
    LDIR
    POP  HL
    JR   main_loop

; -------------------------------------------------------------------------------------------------
; Used Registers A (D7), DE (A1), HL (A2), IX (A0)
; Free Register BC, A', BC', DE', HL'
get_pair
    EX   AF,AF'
    EXX
    INC  IYL                    ; Here IY < 256 always
    LD   C,0                    ; A6 = 0.L

calc_len_dist
    LD   A,C                    ; D0 = A6.W
    AND  $0F                    ; D0 &= $0F
    JR   NZ,node                ; IF D0 == $x0 THEN D5 = 1.W
    LD   HL,1                   ; D5 = 1.W

node
    LD   D,A                    ; Save for the BIT
    LD   A,C                    ; D4 = A6.W (A6 <= 52 .B)
    RRA                         ; D4 >> 1
    LD   (sm_ix + 2),A
sm_ix
    LD   A,(IX + 0)             ; D1 = A0[D4].B (A0 => IX | D4 <= 26)

    BIT  0,D                    ; D4 = 1 | D0 &=D4 =>D0 &= 1 (Because D0 is changed next)
    JR   Z,nibble               ; Use low nibble
    RRA
    RRA
    RRA
    RRA                         ; D1 >> 4 use high nibble (nibble alternating)
nibble
    AND  $0F                    ; D1 &= $0F
    LD   B,A                    ; D1 must go in register B for get_bits

    LD   (sm_d0 + 1),HL         ; D0 = D5.W (In the last pass has the value for sm_d0)

    ; 1 << D1 (D1 = $0 - $F)
    LD   DE,$0000
    CP   8
    JR   C,ponlo_en_e
ponlo_en_d
    SUB  8
    OR   %01011000
    JR   sigue_generando_el_set
ponlo_en_e
    OR   %01111000
sigue_generando_el_set
    RLCA
    RLCA
    RLCA
    LD   (sm_set + 1),A
sm_set
    SET  0,A                    ; Transform in SET x,D or SET x,E

    ADD  HL,DE                  ; D5 += D4.L
    INC  C                      ; A6++
    DEC  IYL                    ; D3--
    JR   NZ,calc_len_dist

    LD   A,B
    EXX
    LD   B,A
    EX   AF,AF'

get_bits
    LD   IY,0
    INC  B

getting_bits
    DJNZ cont_get_bits

sm_d0
    LD   BC,$0000
    ADD  IY,BC
    RET

cont_get_bits
    CALL get_bit
    ; Simulate ADC IY,IY
    JR   NC,solo_duplica_iy
    ADD  IY,IY
    INC  IY                     ; It looks that INC IYL works fine
    JR   getting_bits
solo_duplica_iy
    ADD  IY,IY
    JR   getting_bits

; ---------------------------------------------------------------------------
get_bit
    ADD  A,A
    RET  NZ
    LD   A,(HL)
    INC  HL
    ADC  A,A
    RET
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: TFM on 20:47, 10 October 11
Thank you so much SyX!!! This is alrady a complete wiki article :-)))
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: SyX on 21:13, 10 October 11
Well, we would need to add the results with CPCT and others CPC native crunchers and then we will have the article :)

If you want TFM, i can do it, but tell me what CPC compressors i should test ;)
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: TFM on 21:15, 10 October 11
Quote from: SyX on 21:13, 10 October 11
Well, we would need to add the results with CPCT and others CPC native crunchers and then we will have the article :)

If you want TFM, i can do it, but tell me what CPC compressors i should test ;)

Well, in case we take the French site in account then CPCT and the latest Cheese would be enought I guess. But we can just copy-paste-steal the results from them ;-)
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: Octoate on 23:16, 10 October 11
@SyX: Thanks for your great effort to create a kind of benchmark :)! Btw, maybe CPCAlive (http://www.cpcalive.com/cpcalive_en.html (http://www.cpcalive.com/cpcalive_en.html) - this page is a bit strange...) can help you with testing the CPC cruncher, because it should be possible to use and control CPCAlive directly from the command line and also use files on the harddisk. Maybe you can create a kind of batch file to test the CPC compressors with it.
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: SyX on 11:04, 11 October 11
Thanks Octoate, although i have used WinApe for it... the most boring was waiting to the crunchers finish its task even using the Full Speed/Frame Skip 50/Fast Disk Access (my netbook is guilty :P ),  than prepare the DSK with the files (that is automatized by a shell script).

All the files crunched are 1,2 Megabytes, if somebody want them, only ask ;)

And the table update with the native CPC crunchers is:       |  SIZE|MegaLZ|BITBUS|HRUS21|PCD6.2|RIP.01|CHEESE|CPCT31| CROWN| APLIB|   EXO|PFIREt| PFIRE|   ZIP|    7Z
-------+------+------+------+------+------+------+------+------+------+------+------+------+------+------+------
code-1 | 27932| 12654| 12827| 12865| 12904| 12118| 15771| 14262| 16558| 12222| 12207| 12215| 10833| 12680| 11155
code-2 | 14807|  7767|  8119|  8012|  8090|  7689| 10094|  9510| 11935|  7802|  7597|  7597|  7149|  7904|  7367
code-3 | 35840|  8406|  8181|  8291|  8373|  7891| 10785| 10179| 10772|  7964|  7810|   (1)|  6302|  8667|  6542
-------+------+------+------+------+------+------+------+------+------+------+------+------+------+------+------
scrv-1 |  6912|  4672|  4757|  4705|  4764|  4551|  5219|  5104|  5250|  4692|  4568|  4568|  4430|  4687|  4455
scrv-2 |  6912|  4074|  4170|  4144|  4173|  4030|  4691|  4802|  5317|  4116|  3971|  3970|  3901|  4228|  3980
scrv-3 |  6912|  3604|  3717|  3722|  3753|  3544|  4174|  4273|  4854|  3677|  3517|  3516|  3370|  3679|  3448
scrv-4 |  6912|  2211|  2270|  2359|  2366|  2165|  2783|  2696|  3697|  2228|  2063|  2063|  2008|  2301|  2121
scrv-5 |  6912|  4399|  4470|  4486|  4524|  4298|  5050|  5048|  5558|  4421|  4249|  4249|  4158|  4476|  4173
scrv-6 |  6912|  4233|  4300|  4345|  4364|  4129|  4873|  5084|  5634|  4291|  4093|  4093|  4053|  4297|  4086
scrv-7 |  6912|  3788|  3902|  3921|  3942|  3721|  4534|  4512|  5468|  3800|  3625|  3625|  3506|  3878|  3624
scrv-8 |  6912|  5275|  5345|  5308|  5373|  5139|  5928|  5888|  6480|  5305|  5080|  5088|  4994|  5015|  5344
scrv-9 |  6912|  4958|  5081|  5048|  5095|  4844|  5677|  5732|  6285|  5031|  4818|  4818|  4673|  5035|  4752
-------+------+------+------+------+------+------+------+------+------+------+------+------+------+------+------
text-1 |  6859|  3858|  4077|  4004|  4029|  3726|  5084|  4963|  6133|  3946|  3794|  3794|  3595|  3857|  3751
text-2 | 21746|  7341|  7766|  7549|  7470|  6525| 12202|  8178| 11223|  6878|  6584|  6584|  6047|  6642|  6175
text-3 | 28352| 10252| 11156| 10360| 10246|  8847| 17537| 11304| 15258|  9383|  8990|  8990|  8241|  8955|  8365
text-4 | 39159| 20406| 22246| 20892| 20752| 17334|   (2)| 23343| 30728| 19247| 17830|   (1)| 16451| 17534| 16584
text-5 | 25149| 10443| 11225| 10618| 10515|  9088| 15998| 11754| 16359|  9712|  9293|  9292|  8554|  9236|  8627

(1) Original file is bigger 32KBs, PackFire tiny doesn't compress
(2) Original file is bigger 38KBs, Cheese Cruncher doesn't compress

NOTES:
.- The CPC native crunchers are "Cheese Cruncher v2.2", "CPCT v3.1" and "Crown Cruncher v1.4".
.- All the files sizes are without Amsdos headers.
.- PFIREt is PackFire tiny mode and PFIRE is PackFire normal mode.
.- There is not CPC decruncher for ZIP, 7Z and PackFire normal mode.

It's not a surprise that the cross-platform crunchers (all based in LZ or Huffman algorythms, technology more known in the internet era) are better (not faster although aplib has a faster decruncher) than the native crunchers (normally RLE and similar technology well known in the 80s).
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: redbox on 14:27, 11 October 11
This is great work Syx.


Packfire rulez!  Just need to optimise and it's a real Exomizer beater.


What were you doing with Renegade?
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: TFM on 16:21, 11 October 11
Thank's a lot SyX - great work!!!  :) :) :)

So... the best PC cruncher is "just" 25% better than the best CPC cruncher. Actually not really much. But once a while it will be needed :-)))
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: tastefulmrship on 16:58, 11 October 11
@Syx

Lots of great stuff to think about, thanks!
Out of interest, which version of Packfire were you using? Was it the v1.2h release?


EDIT: Using 1.2g, my two test screens (AMPSKULL.SCR & MASKFACE.SCR) do pack better with PackFire than all of the other external packers. Is there a Z80 decompressor available yet?
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: redbox on 18:05, 11 October 11
SyX provided his port of the Packfire decompressor in his post...
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: tastefulmrship on 18:17, 11 October 11
Quote from: redbox on 18:05, 11 October 11
SyX provided his port of the Packfire decompressor in his post...
Yeah, I guess that's my dumb-move-of-the-day! I even had it in an assembler window in WinAPE!
As the modern philosopher, Homer, would say; "D'oh!"
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: SyX on 18:19, 11 October 11
Quote from: redbox on 14:27, 11 October 11Packfire rulez!  Just need to optimise and it's a real Exomizer beater.
Although that is not an esay task, jejeje, PF is designed to make great use of the 68000 registers and addressing modes by one of the best 68000 assembly coders. He help me to optimize my aplib port to 68000 and we were able to shrink at 164 bytes, only one byte more than the z80 version and we're talking of a cpu with the opcodes of a double size in bytes minimum.

Quote from: redbox on 14:27, 11 October 11What were you doing with Renegade?
I had patched to use the 3 fire buttons joystick that i made a few weeks ago, you can find here (http://www.amstrad.es/forum/viewtopic.php?f=3&t=2498) ;)

Quote from: TFM/FS on 16:21, 11 October 11So... the best PC cruncher is "just" 25% better than the best CPC cruncher. Actually not really much. But once a while it will be needed :-)))
And if you need help to adding at one of your projects only tell me ;)

Jejeje, you know how i'm old school for a few things (the config of my text editor has not changed since the cygnus editor days :P ) and new school for all my cross developing tools, jejeje.

Quote from: tastefulmrship on 16:58, 11 October 11Out of interest, which version of Packfire were you using? Was it the v1.2h release?
I'm using the last version (1.2h), but the sources of the decruncher has not changed from a few versions ago, only the cruncher to improve the compression and fix bugs ;)

Quote from: tastefulmrship on 16:58, 11 October 11EDIT: Using 1.2g, my two test screens (AMPSKULL.SCR & MASKFACE.SCR) do pack better with PackFire than all of the other external packers. Is there a Z80 decompressor available yet?
Remember that i only have converted the tiny mode (params -t when you are crunching and with that the crunched sizes are similar to exomizer). I didn't convert the large mode (is a variant of LZMA (http://en.wikipedia.org/wiki/Lempel%E2%80%93Ziv%E2%80%93Markov_chain_algorithm), tiny is a LZ (http://en.wikipedia.org/wiki/Lempel%E2%80%93Ziv) how aplib and exomizer) because it would be so slow that it would not had practical use in CPC... it's even slow in 68000 and there, it's using every trick in the hat.
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: redbox on 19:00, 11 October 11
Missed your Renegade patch SyX - very nice though.  Didn't realise Amstrad.es has a forum, I need to learn Spanish now (I have been trying French but that is hard, so maybe Spanish will be a nice diversion!).

I love compression because it's real uber programming and maths.  The Packfire compressor and decompressor is very exciting, think I'll take a look through your source and try and see what's going on because for once hopefully I'll understand it because it's in Z80  :)
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: SyX on 20:44, 11 October 11
Quote from: redbox on 19:00, 11 October 11Missed your Renegade patch SyX - very nice though.  Didn't realise Amstrad.es has a forum, I need to learn Spanish now (I have been trying French but that is hard, so maybe Spanish will be a nice diversion!).
Everybody is welcome at the spanish forum, it's full of great content and we don't bite at people talking in other languages :P
Totally agreed, learn a new language is always FUN :)

Quote from: redbox on 19:00, 11 October 11I love compression because it's real uber programming and maths.  The Packfire compressor and decompressor is very exciting, think I'll take a look through your source and try and see what's going on because for once hopefully I'll understand it because it's in Z80  :)
I usually convert or make a compressor to get familiar with a new CPU (my last was convert aplib to 6800, for a Dragon project :) ), because you need to use a great part of the instruction set, it's a much better "hello world" program  ;D

Here is the original 68000 source "hypercomented" (in spanish sorry), you can use to understand better how i converted it:; ------------------------------------------
; PackFire 1.2f - (tiny depacker)
; ------------------------------------------

; ------------------------------------------
; packed data in a0                                     ; A0 = Origen (se usa como puntero a
                                                        ; la tabla de frecuencias)           
; dest in a1                                            ; A1 = Destino
start:                  lea     26(a0),a2               ; A2 = A0 + 26  <- Datos comprimidos

                        move.b  (a2)+,d7                ; D7.B = (A2)   <- 1º Byte comprimido
                                                        ; A2++
                                                        ; Se inicializa el contador de bits
                                                       
lit_copy:               move.b  (a2)+,(a1)+             ; (A1).B = (A2).B <- Copiamos byte
                                                        ; A1++
                                                        ; A2++
main_loop:              bsr.b   get_bit                 ; CALL get_bit <- .B un salto corto
                        bcs.b   lit_copy                ; JR   C,lit_copy <- CS Carry Set
                                                        ; Este último trozo lo que hace es
                                                        ; que mientras se obtengan bits a
                                                        ; 1, iremos copiando bytes de forma
                                                        ; literal.
                       
                        moveq   #-1,d3                  ; D3.L = $FFFFFFFF
get_index:              addq.l  #1,d3                   ; D3++
                        bsr.b   get_bit                 ; CALL get_bit
                        bcc.b   get_index               ; JR   NC,get_index <- CC Carry Clear
                        cmp.w   #$10,d3                 ; ¿D3 == $0010?
                        beq.b   depack_stop             ; JR   Z,depack_stop
                                                        ; Se acabó la descompresión
                                                       
                        bsr.b   get_pair                ; CALL get_pair
                        move.w  d3,d6                   ; D6.W = D3.W <- Lo guarda para
                                                        ; usarlo como contador en copy_bytes
                                                       
                        cmp.w   #2,d3                   ; ¿D3 == $0002?
                        ble.b   out_of_range            ; JR  <=,out_of_range
                                                        ;             <- LE Less or equal
                        moveq   #0,d3                   ; D3.L = 0
                                                        ; En estás 3 últimas líneas lo que
                                                        ; hacen es si D3 > 2, entonces D3=0
                       
out_of_range:           moveq   #0,d0                   ; D0.l = 0
                        move.b  table_len(pc,d3.w),d1   ; D1.B = table_len[D3.W]
                        move.b  table_dist(pc,d3.w),d0  ; D0.B = table_dist[D3.W]
                        bsr.b   get_bits                ; CALL get_bits
                        bsr.b   get_pair                ; CALL get_pair
                                                        ; Se obtiene el offset y la longitud
                                                        ; de la cadena de bytes ya
                                                        ; descomprimida que se va a copiar
                                                        ; a continuación.
                        move.l  a1,a3                   ; A3.L = A1.L
                        sub.l   d3,a3                   ; A3.L -= D3.L
copy_bytes:             move.b  (a3)+,(a1)+             ; (A1).B = (A3).B
                                                        ; A3++
                                                        ; A1++
                        subq.w  #1,d6                   ; D6.W--
                        bne.b   copy_bytes              ; JR   NZ,copy_bytes <- ¿D6 == 0?
                        bra.b   main_loop               ; JR   main_loop

table_len:              dc.b    $04,$02,$04               
table_dist:             dc.b    $10,$30,$20               

get_pair:               sub.l   a6,a6                   ; A6.L = 0
                        moveq   #$f,d2                  ; D2.L = $0000000F <- D2 es constante
calc_len_dist:          move.w  a6,d0                   ; D0.W = A6.W
                        and.w   d2,d0                   ; D0.W &= D2.W <- D0.W 0-$F
                        bne.b   node                    ; JR   NZ,node
                        moveq   #1,d5                   ; D5.L = 1
node:                   move.w  a6,d4                   ; D4.W = A6.W
                        lsr.w   #1,d4                   ; D4.W >> 1
                        move.b  (a0,d4.w),d1            ; D1 = A0[D4.W] <- Se lee un byte
                                                        ; de la tabla de frecuencias, por lo
                                                        ; que D4 < 26 ó lo que es lo mismo
                                                        ; A6 < 26 * 2, lo cual nos
                                                        ; permitirá usar un registro de 8
                                                        ; bits del Z80.
                                                        ;
                        moveq   #1,d4                   ; D4.L = 1
                        and.w   d4,d0                   ; D0.W &= D4.W <- D0.W &= 1
                        beq.b   nibble                  ; JR   NZ,nibble
                                                        ; Podemos sustituir las tres últimas
                                                        ; instrucciones por:
                                                        ; BIT 0,D0 / JR Z,nibble
                        lsr.b   #4,d1                   ; D1.B >> 4
                                                        ; Lo que se ha hecho es seleccionar
                                                        ; entre el nibble de más peso ó
                                                        ; menos peso del byte leido de la
                                                        ; tabla de frecuencias (así que mas
                                                        ; que 26 bytes, son 52 nibbles), y ; se realiza de forma alternativa,
                                                        ; empezando por el bajo.
                                                       
nibble:                 move.w  d5,d0                   ; D0.W = D5.W
                        and.w   d2,d1                   ; D1.W &= $F <- D1.W 0-$F
                                                        ; nos quedamos solo con el nibble
                        lsl.l   d1,d4                   ; D4.L << D1 <- 1 << D1
                                                        ; D4 = 2^D1 <- 1 - 32768
                        add.l   d4,d5                   ; D5.L += D4.L
                        addq.w  #1,a6                   ; D6.W++
                                                        ; Recordar que D6 < 26 * 2
                        dbf     d3,calc_len_dist        ; D3.W--
                                                        ; ¿D3 == $FFFF?
                                                        ; JR   NZ,calc_len_dist
                                                        ; En el 68000, su DJNZ es hasta -1
                                                        ; en lugar de a 0, como en el Z80.
                                                       
get_bits:               moveq   #0,d3                   ; D3.L = 0
getting_bits:           subq.b  #1,d1                   ; D1.B--
                        bhs.b   cont_get_bit            ; JR   NC,cont_get_bit <- HS = CC
                        add.w   d0,d3                   ; D3.W += D0.W
depack_stop:            rts                             ; RET <- Por aquí se sale también
cont_get_bit:           bsr.b   get_bit                 ; CALL get_bit
                        addx.l  d3,d3                   ; D3 = D3 * 2 + Carry
                                                        ; En el registro de estado del 68000
                                                        ; a parte del Acarreo, hay una
                                                        ; bandera X (eXtended) que se usa
                                                        ; como bit de más peso en las
                                                        ; operaciones matemáticas, aunque
                                                        ; normalmente es una copia del
                                                        ; Acarreo, como en este caso, no
                                                        ; siempre lo es.
                        bra.b   getting_bits            ; JR   getting_bits
                       
get_bit:                add.b   d7,d7                   ; D7 << 1
                        bne.b   byte_done               ; JR   NZ,byte_done <- RET NZ
                        move.b  (a2)+,d7                ; D7.B = (A2)
                                                        ; A2++
                        addx.b  d7,d7                   ; D7 = D7 * 2 + Carry
byte_done:              rts                             ; RET
                                                        ; Esta es la típica rutina para
                                                        ; extraer bits de los datos
                                                        ; comprimidos.
                                                       
Title: Exomizer article on CPCWiki
Post by: Nich on 21:15, 11 October 11
Quote from: Nich on 11:45, 09 October 11
I really ought to write a CPCWiki article on how to use Exomizer with a CPC... ::)
I've done it (http://cpcwiki.eu/index.php/Exomizer)! :D It's rather verbose, and it assumes that you are using a Windows machine (sorry, Linux users! ;)), and there are still some things I want to add to the article, such as how to use backwards compression. I also want to provide a version of the decompression routines that actually work with WinAPE without having to make significant corrections to it. Let me know what you think of the article!
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: SyX on 21:35, 11 October 11
It looks Great Nich!!!  :D

I think is perfect for everybody interested in how use a cross compresor (all works exactly the same) in his projects and kudos for explain the safety offset, not everybody know that feature ;)
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: ervin on 23:13, 11 October 11
Fantastic stuff Nich!
I'm going to find that very handy indeed.
Thanks!
Title: Re: Exomizer article on CPCWiki
Post by: Executioner on 00:31, 12 October 11
Quote from: Nich on 21:15, 11 October 11
I also want to provide a version of the decompression routines that actually work with WinAPE without having to make significant corrections to it.

There's actually only a couple of minor changes:

1. Remove the : from the comment line at the top or add an extra ;
2. Remove one t from the gett4bits label
3. Replace the [] with () for all the [iy+d] instructions

Maybe these changes should be recommended to the original author, and maybe WinAPE should support square brackets for indexed addressing even though it's not MAXAM compatible.
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: redbox on 10:16, 12 October 11
Nice work Nich.


The decompressor on the CPCRulez website (http://cpcrulez.fr/applications_tools_cruncher_exomiser2_Z80.htm) assembles with Maxam/WinAPE out of the box.


I think you just need to Remark one of the comments at the bottom.
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: TFM on 17:18, 12 October 11
Quote from: SyX on 18:19, 11 October 11
And if you need help to adding at one of your projects only tell me ;)

Actually I take that offer for our Giana Sister Clone :-) I intend to continue this project now, had no time to work at it since February. I come back to crunching as soon as needed :-)))
Title: Re: Exomizer article on CPCWiki
Post by: Nich on 19:08, 12 October 11
Quote from: Executioner on 00:31, 12 October 11
There's actually only a couple of minor changes:

1. Remove the : from the comment line at the top or add an extra ;
2. Remove one t from the gett4bits label
3. Replace the [] with () for all the [iy+d] instructions

Maybe these changes should be recommended to the original author, and maybe WinAPE should support square brackets for indexed addressing even though it's not MAXAM compatible.
Is it possible for you to fix the bug that prevents colons from being included within comments?
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: redbox on 19:18, 12 October 11
Just double colon ;; at the start of the comment.
Title: Re: Exomizer article on CPCWiki
Post by: Executioner on 23:59, 13 October 11
Quote from: Nich on 19:08, 12 October 11
Is it possible for you to fix the bug that prevents colons from being included within comments?

If it were a bug, I'd fix it, but Maxam does the same. I'm thinking maybe I could set up some default options where this (and eg. operator precedence) could be changed just by adding assembler options.
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: TFM on 18:19, 14 October 11
The Executioner is right.

This is not a bug, it's a feature! It allows to add code after comments in the same line. And it's good to have it that way.

Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: Nich on 19:25, 16 October 11
Quote from: TFM/FS on 18:19, 14 October 11
This is not a bug, it's a feature! It allows to add code after comments in the same line. And it's good to have it that way.
??? Why would you want to do that? Every programming example I've seen puts comments after the code if the comment is on the same line.

Anyway, if the 'bug' is a feature of Maxam, then I accept Executioner's decision not to fix this problem.
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: Executioner on 23:46, 17 October 11
Quote from: Nich on 19:25, 16 October 11
??? Why would you want to do that? Every programming example I've seen puts comments after the code if the comment is on the same line.

I agree it's a bit silly, and I'd like to fix it, but that may break a lot of existing code. Maybe instead of a load of options in the files allowing you to change the way WinAPE assembler works there could be one check box, "Strict Maxam Compatibility" which enabled code after comments, and disabled such things as macros. Problem is you'd need to turn it on/off for different files, so it may be better to put something like ;;$M at the top of any file you want strict compatibility in.
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: TFM on 22:13, 18 October 11
Quote from: Nich on 19:25, 16 October 11
??? Why would you want to do that? Every programming example I've seen puts comments after the code if the comment is on the same line.

Haha, have you ever seen Odiesofts Code? Every line is nearly full (250 chars?). Opcodes, Comments, Opcodes ... Why?  Because memory is limited, and the READ instruction is limited. We're talking about a CPC, not emulation.

So my code it nice at the beginning, but with adding more functions sometimes every character has to be saved to be pressed in a single file.

However, that's the way we did it in the old days (and I like still to work that way, without PCs!). Today everybody first buys a PC to be able to program for the CPC. Today you don't care about RAM and filesize, but in the old days it was different. And THEREFORE Arnor was smart enought to introduce that FEATURE  :laugh:
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: TFM on 22:17, 18 October 11
Quote from: Executioner on 23:46, 17 October 11
I agree it's a bit silly, and I'd like to fix it, but that may break a lot of existing code. Maybe instead of a load of options in the files allowing you to change the way WinAPE assembler works there could be one check box, "Strict Maxam Compatibility" which enabled code after comments, and disabled such things as macros. Problem is you'd need to turn it on/off for different files, so it may be better to put something like ;;$M at the top of any file you want strict compatibility in.

This is now very IMHO.... It I have to assemble code then I have no time to waste. So I can use WinApe and if it works then it's great! But it there are problems, then I will just take another assembler - for me this is MAXAM on ROM. And if I use that under Winape then it runs very quick. But I will not waste time to search the problem of incompatibiltity. Maybe other people think the same way. So what ever you do, IMHO it would be great to keep it easy  :) :) :)
Title: Re: Exomizer article on CPCWiki
Post by: Metalbrain on 19:19, 17 January 12
Hi all!
I've just seen the CPCWiki article only uses the official exomizer release, and therefore you don't get my optimizations. Anyway, the depackers have been recently optimized by Antonio Villena, and I'm gonna start a thread about it.
Quote from: Executioner on 00:31, 12 October 11

2. Remove one t from the gett4bits label
3. Replace the [] with () for all the [iy+d] instructions
Ops  :-[ , I don't know how those got there in the official exomizer release, I guess I didn't check it too much because it happened like ten months after I had released my depackers. The new versions I just sent to Magnus Lind shouldn't have those bugs.
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: Metalbrain on 19:35, 17 January 12
Quote from: SyX on 18:26, 10 October 11Apropos of compressor (the Babel subject is other world, jejejeje, and wait to add the dialects to the discussion ;) ), i don't trust in exomizer, i have used in a few projects without problems even in backward mode, but i have crunched a few files that the z80 decruncher can not decrunch and passed a lot of time debugging my code :-[
Do you still have those files?
Quote from: SyX on 18:26, 10 October 11i have converted packfire (http://www.pouet.net/prod.php?which=54840) tiny mode to z80, and how aplib, it doesn't need a buffer in ram how exomizer (the table is in the first 26 bytes of every crunched file) and the decrunched files are the same size that exomizer (or even a few bytes smaller),  but is much much more slower and the tiny mode only can compress up 32 KBs, not a single byte more.
When I first converted exomizer depackers to Z80, I noticed the format was wasting 2 bits, so I made an optimizer to cut those 2 bits and also resort the bit stream to be read from left to right (faster on Z80 thanks to ADD instructions). Checking Packfire's tiny mode, I noticed it's basically the same as exomizer but cutting one of those redundant bits from the "official exomizer 2 format", but not the other one, so it only has a 12,5% of probability to improve the resulting size in one byte, not a 25% like my optimizator has  :P .
The fact that your depacker needs no table is interesting, but I'm not sure if the extra time it takes to get the info from the minitable is really worth it.
Title: Re: Dumb question #15839 - BITBUSTER 1.2
Post by: SyX on 21:02, 17 January 12
Quote from: Metalbrain on 19:35, 17 January 12Do you still have those files?
I think no, it happened mainly when i was making the tapes for the Mojon Twins games (a problem with a sequence of opcodes generated by z88dk!?!?!?!?), but i will give a test to your new version and if i get another "decrunching bug" i will send you :)

Quote from: Metalbrain on 19:35, 17 January 12The fact that your depacker needs no table is interesting, but I'm not sure if the extra time it takes to get the info from the minitable is really worth it.
Yes, those are the problems, bu it was more a proof of concept and an exercise for refreshing my 68000, the "damned" decruncher abuse of 68000 registers and addressing modes, so much flexibles that our poor z80 :P , i had to use self-modify code and that is not always the best solution for so little code
Powered by SMFPacks Menu Editor Mod