*********************************
***  CrMData V1.01            ***
***  (c) 1993 Thomas Schwarz  ***
*********************************
	incdir	dh0:ass/Include/
	include	exec/exec_lib.i
	include	dos/dos_lib.i
	include	dos/dosextens.i
	include	utility/tagitem.i
	incdir	dh1:t/ass/Include/
	include	libraries/CrM.i
	include	libraries/CrM_lib.i
*************************************************
CALL	MACRO
	jsr	_LVO\1(a6)
	ENDM
CALLEXEC MACRO
	move.l	4.w,a6
	CALL	\1
	ENDM
CALLCRM	MACRO
	move.l	_CrMBase(pc),a6
	CALL	\1
	ENDM
CALLDOS MACRO
	move.l	_DOSBase(pc),a6
	CALL	\1
	ENDM
*************************************************
CrunchOnly	equ	1
DecrunchOnly	equ	2
ExtraMemLen	equ	100
*************************************************
main:
	lea	CommandLine(pc),a1
	movem.l	d0/a0,(a1)		;save CLI-Parameters

** Open dos.library: **
	lea	DOSName(pc),a1
	CALLEXEC OldOpenLibrary
	lea	_DOSBase(pc),a0
	move.l	d0,(a0)
	beq.s	.End

** Get output handle: **
	move.l	d0,a6
	CALL	Output
	lea	OutHandle(pc),a0
	move.l	d0,(a0)
	beq.s	.CloseDOS

** Open CrM.library: **
	lea	CrMName(pc),a1
	moveq	#4,d0
	CALLEXEC OpenLibrary
	lea	_CrMBase(pc),a0
	move.l	d0,(a0)
	beq.s	.CloseDOS

** Do all actions: **
	bsr.s	mainloop

** Close CrM.library: **
	move.l	_CrMBase(pc),a1
	CALLEXEC CloseLibrary
** Close dos.library: **
.CloseDOS:
	move.l	_DOSBase(pc),a1
	CALLEXEC CloseLibrary
** Return to the CLI: **
.End:	moveq	#0,d0
	rts
*----------
mainloop:
	lea	InitTxt(pc),a0
	bsr.w	PrintText

** Analyse Commandline: **
	movem.l	CommandLine(pc),d1/a1	;get Parameters
	clr.b	-1(a1,d1.w)		;replace <cr> by Null
	move.b	(a1),d0
	beq.w	.usage			;no Parameters
	cmp.b	#"?",d0
	beq.w	.usage			;question mark -> print usage
	lea	Algorithm(pc),a2
	move.w	(a2),d1			;default Algorithm
	cmp.b	#"-",d0
	bne.w	.noopts			;no option specified
	addq.l	#1,a1

** Optionsloop: processes all options, no spaces between options are allowed!
.optsloop:
	move.b	(a1)+,d0		;get char
	beq.w	.usage
	cmp.b	#" ",d0
	beq.w	.noopts			;no more options

	cmp.b	#"1",d0
	beq.s	.norm
	cmp.b	#"2",d0
	beq.s	.lzh
	cmp.b	#"c",d0
	beq.s	.crunch
	cmp.b	#"d",d0
	beq.s	.decrunch
	cmp.b	#"f",d0
	beq.s	.flash
	cmp.b	#"l",d0
	beq.s	.longer
	cmp.b	#"s",d0
	beq.s	.sample
	cmp.b	#"y",d0
	beq.s	.encrypt
	lea	UnknownOpt(pc),a0
	move.b	d0,(a0)
	lea	UnknownOptTxt(pc),a0
	bsr.w	PrintText
	bra.s	.optsloop
*-----
.norm:	and.w	#$fff0,d1		;kill old algorithm
	or.w	#cm_Normal,d1		;new algo
	bra.s	.optsloop
*-----
.lzh:	and.w	#$fff0,d1		;kill old algorithm
	or.w	#cm_LZH,d1		;new algo
	bra.s	.optsloop
*-----
.crunch:
	lea	Operation(pc),a0
	move.b	#CrunchOnly,(a0)
	bra.s	.optsloop
*-----
.decrunch:
	lea	Operation(pc),a0
	move.b	#DecrunchOnly,(a0)
	bra.s	.optsloop
*-----
.flash:
	bset	#cmB_LEDFlash,d1
	bra.s	.optsloop
*-----
.longer:
	lea	LongerFileFlag(pc),a0
	st	(a0)
	bra.w	.optsloop
*-----
.sample:
	bset	#cmB_Sample,d1
	bra.w	.optsloop
*-----
.encrypt:
	bset	#cmB_PW,d1
	bra.w	.optsloop
*-----
.noopts:
	move.w	d1,(a2)			;algorithm
	lea	SourceName(pc),a0
	move.l	a1,(a0)
	lea	DestName(pc),a0		;normally Source- and DestName are
	move.l	a1,(a0)			;the same...
.search:
	move.b	(a1)+,d0
	beq.s	.samedest		;no second filename
	cmp.b	#" ",d0
	bne.s	.search
	move.l	a1,(a0)			;new DestName
	clr.b	-1(a1)			;replace <Space> by Null
.samedest:

** Open Sourcefile: **
	move.l	SourceName(pc),d1
	move.l	#MODE_OLDFILE,d2
	CALLDOS	Open
	move.l	d0,d5
	beq.w	.srcnotopen

** Read DataHeader (first 14 Bytes in the file): **
	move.l	d5,d1
	lea	DataHdr(pc),a0
	move.l	a0,d2
	moveq	#14,d3
	CALL	Read

	lea	DataHdr(pc),a0
	CALLCRM	cmCheckCrunched
	lea	Operation(pc),a0
	tst.l	d0
	beq.s	.loadnormal		;file is not crunched with CrM
	cmp.b	#CrunchOnly,(a0)
	beq.w	.alreadycrunched	;can't crunch twice!
	move.b	#DecrunchOnly,(a0)
	bsr.w	CrunchedLoad		;load crunched file
	bra.s	.crloadcont
.loadnormal:
	cmp.b	#DecrunchOnly,(a0)
	beq.w	.notcrunched
	move.b	#CrunchOnly,(a0)
	bsr.w	NormalLoad		;load original file
.crloadcont:
	move.l	d0,-(sp)		;save return code
	move.l	d5,d1
	CALLDOS	Close			;close Sourcefile
	move.l	(sp)+,d0
	beq.s	.done			;loading failed!

	move.b	Operation(pc),d0
	cmp.b	#DecrunchOnly,d0
	bne.s	.nodecr
	bsr.w	DecrunchIt		;decrunch data
	beq.s	.done
.nodecr:
	move.b	Operation(pc),d0
	cmp.b	#DecrunchOnly,d0
	bne.s	.nodecrsave
	bsr.w	DecrunchedSave		;save original data
.nodecrsave:
	move.b	Operation(pc),d0
	cmp.b	#CrunchOnly,d0
	bne.s	.nocr
	bsr.w	CrunchIt		;crunch data
	beq.s	.done
.nocr:
	move.b	Operation(pc),d0
	cmp.b	#CrunchOnly,d0
	bne.s	.nocrsave
	bsr.w	CrunchedSave		;save crunched data
.nocrsave:

.done:
** Free cmCrunchStruct: **
	move.l	CrStruct(pc),d0
	beq.s	.nocrstruct		;no cmCrunchStruct allocated
	move.l	d0,a1
	moveq	#cm_FreeStruct,d0
	CALLCRM	cmProcessCrunchStructA
.nocrstruct:
** Free Buffer: **
	move.l	MemBase(pc),a1
	move.l	MemLen(pc),d0
	beq.s	.End
	CALLEXEC FreeMem
.End:	rts
*-------
** Sourcefile open failed! **
.srcnotopen:
	move.l	SourceName(pc),a0
	move.l	a0,-(sp)
	lea	NotOpenTxt(pc),a0
	move.l	sp,a1
	bsr.s	RawPrintText
	addq.l	#4,sp
	rts
*-------
** DecrunchOnly: File is not crunched **
.notcrunched:
	lea	NotCrunchedTxt(pc),a0
.acrcont:
	move.l	SourceName(pc),-(sp)
	move.l	sp,a1
	bsr.s	RawPrintText
	addq.l	#4,sp
	moveq	#0,d0
	bra.w	.crloadcont
*-----
** CrunchOnly: File is already crunched **
.alreadycrunched:
	lea	AlreadyCrTxt(pc),a0
	bra.s	.acrcont
*-------
** Print Usage: **
.usage:	lea	UsageTxt(pc),a0
;	bra.s	PrintText
********************************
** Print some text to the CLI **
PrintText:	** a0:Text
	movem.l	d0-d3/a0-a1/a6,-(sp)
	move.l	a0,d2
	move.l	OutHandle(pc),d1
	moveq	#-1,d3
.count:	addq.l	#1,d3
	tst.b	(a0)+
	bne.s	.count
	CALLDOS	Write
	movem.l	(sp)+,d0-d3/a0-a1/a6
	rts
*----------
** Print some text to the CLI with formatting using RawDoFmt(): **
RawPrintText:	** a0:Text a1:Args
	movem.l	d0-d2/a0-a3/a6,-(sp)
	lea	.stuffchar(pc),a2
	lea	InitTxt(pc),a3
	CALLEXEC RawDoFmt
	lea	InitTxt(pc),a0
	bsr.s	PrintText		;print the converted text
	movem.l	(sp)+,d0-d2/a0-a3/a6
	rts
*-----
.stuffchar:
	move.b	d0,(a3)+		;put data to output string
	rts
*****************************
** Load a file to crunch it. A cmCrunchStruct and the Buffer for the file
** will be allocated.
NormalLoad:
** Get Lock on the Sourcefile: **
	move.l	SourceName(pc),d1
	moveq	#ACCESS_READ,d2
	CALLDOS	Lock
	move.l	d0,d4
	beq.w	.notopen		;locking failed!

** Examine Sourcefile: **
	move.l	d4,d1
	lea	InitTxt(pc),a0		;InitTxt serves as buffer for the fib
	move.l	a0,d2
	CALL	Examine
	move.l	d0,-(sp)		;save result on the stack

** UnLock Sourcefile: **
	move.l	d4,d1
	CALL	UnLock
	move.l	(sp)+,d0
	beq.w	.notopen		;examining failed!
	lea	InitTxt(pc),a0
	move.l	fib_Size(a0),d7		;Size of Sourcefile

** Allocate Buffer (Len=Sourcefilelength+ExtraMemLen): **
	moveq	#ExtraMemLen,d0
	add.l	d7,d0
	lea	MemLen(pc),a0
	move.l	d0,(a0)
	moveq	#0,d1
	CALLEXEC AllocMem
	lea	MemBase(pc),a0
	move.l	d0,(a0)
	beq.w	.nomem			;not enough memory

** Allocate a cmCrunchStruct: **
	clr.l	-(sp)			;TAG_DONE
	move.w	Algorithm(pc),-(sp)
	clr.w	-(sp)
	move.l	#CMCS_Algo,-(sp)
	move.l	sp,a0
	moveq	#cm_AllocStruct,d0
	CALLCRM	cmProcessCrunchStructA
	lea	12(sp),sp
	lea	CrStruct(pc),a0
	move.l	d0,(a0)
	beq.s	.nomem			;allocating failed

	move.l	d7,-(sp)
	move.l	SourceName(pc),a0
	move.l	a0,-(sp)
	lea	LoadingTxt(pc),a0
	move.l	sp,a1
	bsr.w	RawPrintText
	addq.l	#8,sp

** Copy DataHeader to Buffer **
	move.l	MemBase(pc),a1
	add.w	#ExtraMemLen,a1
	lea	DataHdr(pc),a0
	move.l	(a0)+,(a1)+
	move.l	(a0)+,(a1)+
	move.l	(a0)+,(a1)+
	move.w	(a0)+,(a1)+

** Load rest of sourcefile **
	move.l	d5,d1
	move.l	a1,d2
	move.l	d7,d3
	subq.l	#8,d3
	subq.l	#6,d3
	CALLDOS	Read
	cmp.l	d0,d3
	bne.s	.readerr		;readerror

	lea	OrigLen(pc),a0
	move.l	d7,(a0)			;Originallen (Length of Sourcefile)
	lea	ReturnTxt(pc),a0
	bsr.w	PrintText

	moveq	#1,d0			;return: TRUE
	rts
*-----
** Opening failed: **
.notopen:
	move.l	SourceName(pc),a0
	move.l	a0,-(sp)
	lea	NotOpenTxt(pc),a0
	move.l	sp,a1
	bsr.w	RawPrintText
	addq.l	#4,sp
.Exit:	moveq	#0,d0			;return: FALSE
	rts
*-----
** not enough memory available: **
.nomem:	lea	MemLen(pc),a0
	clr.l	(a0)
	lea	NoMemTxt(pc),a0
.prtx:	bsr.w	PrintText
	bra.s	.Exit
** readerror: **
.readerr:
	lea	ReadErrTxt(pc),a0
	bra.s	.prtx
*------------
** Crunch Data: **
CrunchIt:
	lea	CrunchingTxt(pc),a0
	bsr.w	PrintText

	move.l	CrStruct(pc),a0
	move.l	MemBase(pc),a1
	move.l	a1,cmcr_Dest(a0)
	moveq	#ExtraMemLen,d0
	add.l	d0,a1
	move.l	a1,cmcr_Src(a0)
	move.l	OrigLen(pc),d1
	move.l	d1,cmcr_SrcLen(a0)
	add.l	d0,d1
	move.l	d1,cmcr_DestLen(a0)
	lea	DataHdr(pc),a1
	move.l	a1,cmcr_DataHdr(a0)
	clr.l	cmcr_DisplayHook(a0)
	move.w	#$7ffe,cmcr_DisplayStep(a0)
	CALLCRM	cmCrunchData

	lea	CrLen(pc),a0
	move.l	d0,(a0)
	beq.s	.error			;error while crunching

** calculate gain in percent: you have to do this complicated rotating
** because there is no longword division available on a standard 68000
** this routine is not very cool, it will produce shit when the gain is
** negative. (Problem now fixed).
	move.l	OrigLen(pc),d1
	move.l	d1,d2
	move.l	d1,d3
	moveq	#0,d4
	sub.l	d0,d2			;gain
	bpl.s	.rotloop
	neg.l	d2
	moveq	#1,d4
.rotloop:
	tst.l	d2
	bmi.s	.rotend
	tst.l	d3
	bmi.s	.rotend
	add.l	d2,d2
	add.l	d3,d3
	bra.s	.rotloop
.rotend:
	lsr.l	#1,d2
	lsr.l	#1,d3
	clr.w	d2
	clr.w	d3
	swap	d2
	swap	d3
	mulu	#100,d2
	divu	d3,d2
	tst.w	d4
	beq.s	.noneg
	neg.w	d2
.noneg:	move.w	d2,-(sp)
	move.l	d0,-(sp)
	move.l	d1,-(sp)
	move.l	sp,a1
	lea	CrunchedTxt(pc),a0
	bsr.w	RawPrintText
	lea	10(sp),sp
	moveq	#1,d0			;return: TRUE
	rts

** error while crunchung: **
.error:	move.l	CrStruct(pc),a0
	move.b	cmcr_QuitFlag(a0),d0
	lea	AbortTxt(pc),a0
	cmp.b	#"a",d0
	beq.s	.errend		;crunching was aborted (not possible yet)
	lea	NotCrTxt(pc),a0
	cmp.b	#"n",d0
	beq.s	.errend		;data is not crunchable (or already
				;crunched with another packer)
	lea	UnknownErrTxt(pc),a0
.errend:
	bsr.w	PrintText
	moveq	#0,d0		;return: FALSE
	rts
*----------
** Save crunched data: **
CrunchedSave:
** Open Destination file: **
	move.l	OrigLen(pc),d0
	sub.l	CrLen(pc),d0
	subq.l	#8,d0
	subq.l	#6,d0
	bgt.s	.cont
	move.b	LongerFileFlag(pc),d0
	bne.s	.cont			;keep longer files
	lea	TooLongFileTxt(pc),a0
	bra.w	RawPrintText
*-----
.cont:	move.l	DestName(pc),d1
	move.l	#MODE_NEWFILE,d2
	CALLDOS	Open
	move.l	d0,d5
	beq.s	.notopen		;open failed

	moveq	#14,d0
	add.l	CrLen(pc),d0
	move.l	d0,-(sp)
	move.l	DestName(pc),-(sp)
	move.l	sp,a1
	lea	SavingTxt(pc),a0
	bsr.w	RawPrintText
	addq.l	#8,sp

** Write DataHeader: **
	move.l	d5,d1
	lea	DataHdr(pc),a0
	move.l	a0,d2
	moveq	#14,d3
	CALL	Write			;DataHeader
	tst.l	d0
	bmi.s	.error			;writeerror

** Write crunched Data: **
	move.l	d5,d1
	move.l	MemBase(pc),d2
	move.l	CrLen(pc),d3
	CALL	Write			;Data
	tst.l	d0
	bmi.s	.error			;writeerror

** Close Destination file: **
	move.l	d5,d1
	CALL	Close

** Generate Comment: **
	lea	Comment(pc),a0
	move.l	OrigLen(pc),-(sp)
	move.l	sp,a1
	lea	.stuffchar(pc),a2
	lea	InitTxt(pc),a3		;again InitTxt serves as a temporary
					;buffer
	CALLEXEC RawDoFmt
	addq.l	#4,sp

** Set Comment (for RTDD): **
	move.l	DestName(pc),d1
	lea	InitTxt(pc),a0
	move.l	a0,d2
	CALLDOS	SetComment

	lea	ReturnTxt(pc),a0
	bra.w	PrintText		;print texte and return (no returncode)
*-----
** Destfile open failed: **
.notopen:
	move.l	DestName(pc),-(sp)
	move.l	sp,a1
	lea	NotOpenTxt(pc),a0
	bsr.w	RawPrintText
	addq.l	#4,sp
	rts
*-----
** writeerror: **
.error:	lea	ErrorWriteTxt(pc),a0
	bsr.w	PrintText

** close destfile: **
	move.l	d5,d1
	CALL	Close

** delete destfile: **
	move.l	DestName(pc),d1
	CALL	DeleteFile
	rts
*-----
.stuffchar:
	move.b	d0,(a3)+		;put data to output string
	rts
*****************************
** Load data to decrunch (Buffer will be allocated): **
CrunchedLoad:
** Copy contents of DataHeader to internal Variables: **
	lea	DataHdr(pc),a0
	lea	OrigLen(pc),a1
	move.l	dh_OriginalLen(a0),(a1)
	lea	CrLen(pc),a1
	move.l	dh_CrunchedLen(a0),(a1)

** Allocate Buffer (len=OrigLen+MinSecDist): **
	moveq	#0,d0
	move.w	dh_MinSecDist(a0),d0
	add.l	dh_OriginalLen(a0),d0
	lea	MemLen(pc),a0
	move.l	d0,(a0)
	moveq	#0,d1
	CALLEXEC AllocMem
	lea	MemBase(pc),a0
	move.l	d0,(a0)
	beq.w	.nomem			;not enough memory

	moveq	#14,d0
	add.l	CrLen(pc),d0
	move.l	d0,-(sp)
	move.l	SourceName(pc),-(sp)
	move.l	sp,a1
	lea	LoadingTxt(pc),a0
	bsr.w	RawPrintText
	addq.l	#8,sp

** Read crunched Data: **
	move.l	d5,d1
	move.l	MemBase(pc),d2
	move.l	CrLen(pc),d3
	CALLDOS	Read
	cmp.l	d0,d3
	bne.s	.readerr		;readerror

	moveq	#1,d0			;return: TRUE
	lea	ReturnTxt(pc),a0
	bra.s	.prtx
*-----
.readerr:
	moveq	#0,d0			;return: FALSE
	lea	ReadErrTxt(pc),a0
	bra.s	.prtx
*-----
.nomem:	lea	MemLen(pc),a0
	clr.l	(a0)
	moveq	#0,d0			;return: FALSE
	lea	NoMemTxt(pc),a0
.prtx:	bra.w	PrintText
*------------
** Decrunch Data: **
DecrunchIt:
	move.l	OrigLen(pc),-(sp)
	move.l	CrLen(pc),-(sp)
	move.l	sp,a1
	lea	DecrunchingTxt(pc),a0
	bsr.w	RawPrintText
	addq.l	#8,sp

	lea	DataHdr(pc),a2
	move.l	MemBase(pc),a0
	move.w	dh_MinSecDist(a2),d0
	lea	0(a0,d0.w),a1
	CALLCRM	cmDecrunch
	tst.l	d0
	beq.s	.error

	lea	ReturnTxt(pc),a0
	bsr.w	PrintText
	moveq	#1,d0			;return: TRUE
	rts
*-----
** error while decrunching: **
.error:
	lea	DecrErrorTxt(pc),a0
	bsr.w	PrintText
	moveq	#0,d0			;return: FALSE
	rts
*----------
** Save original (decrunched) file: **
DecrunchedSave:
** Open Destination file: **
	move.l	DestName(pc),d1
	move.l	#MODE_NEWFILE,d2
	CALLDOS	Open
	move.l	d0,d5
	beq.s	.notopen		;openfail

	move.l	OrigLen(pc),-(sp)
	move.l	DestName(pc),-(sp)
	move.l	sp,a1
	lea	SavingTxt(pc),a0
	bsr.w	RawPrintText
	addq.l	#8,sp

** Write Data: **
	move.l	d5,d1
	lea	DataHdr(pc),a0
	moveq	#0,d2
	move.w	dh_MinSecDist(a0),d2
	add.l	MemBase(pc),d2
	move.l	OrigLen(pc),d3
	CALL	Write			;Data
	tst.l	d0
	bmi.s	.error			;writeerror

** Close File: **
	move.l	d5,d1
	CALL	Close

	lea	ReturnTxt(pc),a0
	bra.w	PrintText		;print text and return (no returncode)
*-----
** destfile could not be opened: **
.notopen:
	move.l	DestName(pc),-(sp)
	move.l	sp,a1
	lea	NotOpenTxt(pc),a0
	bsr.w	RawPrintText
	addq.l	#4,sp
	rts
*-----
** writeerror: **
.error:	lea	ErrorWriteTxt(pc),a0
	bsr.w	PrintText

** Close destfile: **
	move.l	d5,d1
	CALL	Close

** Delete destfile: **
	move.l	DestName(pc),d1
	CALL	DeleteFile
	rts
*************************************************
_DOSBase:	dc.l	0
_CrMBase:	dc.l	0
OutHandle:	dc.l	0		;Handle to print text in the CLI
MemBase:	dc.l	0		;Start of Buffer
MemLen:		dc.l	0		;Length of Buffer
OrigLen:	dc.l	0		;Original Length of Data
CrLen:		dc.l	0		;Crunched Length if Data
CrStruct:	dc.l	0		;struct cmCrunchStruct *
CommandLine:	dc.l	0,0		;CLI-Parameters (text *, len)
SourceName:	dc.l	0		;Sourcefilename *
DestName:	dc.l	0		;Destinationfilename *
DataHdr:	ds.b	14		;struct DataHeader
Algorithm:	dc.w	cm_LZH!cmF_Overlay	;Algorithm for cmcs_Algo Tag
Operation:	dc.b	0		;type of Operation (CrunchOnly,
					;DecrunchOnly or NULL for auto)
LongerFileFlag:	dc.b	0		;keep longer files?
DOSName:	dc.b	"dos.library",0
CrMName:	CRMNAME
		cnop	0,4
InitTxt:	dc.b	27,"[33;1mCrMData ",27,"[0;33mV1.01 ",27,"[0m--- "
		dc.b	27,"[32m(c) 1993 Thomas Schwarz",27,"[0m",10,10,0
		dc.b	"$VER: CrMData 1.01",0
UsageTxt:	dc.b	"Usage: CrMData [-12cdfsy] <sourcefile> [<destfile>]",10
		dc.b	"-1 : use CrM-Normal algorithm",10
		dc.b	"-2 : use LZ-Huffman algorithm",10
		dc.b	"-c : crunch only",10
		dc.b	"-d : decrunch only",10
		dc.b	"-f : enable Power-LED flashing",10
		dc.b	"-l : save file, even if it becomes longer",10
		dc.b	"-s : use Sample-Mode",10
		dc.b	"-y : enable password encryption",10,0
UnknownOptTxt:	dc.b	"Unknown option: -"
UnknownOpt:	dc.b	" !"
ReturnTxt:	dc.b	10,0
NotOpenTxt:	dc.b	"Could not open `%s'!",10,0
LoadingTxt:	dc.b	"Loading `%s' (%ld bytes)...",0
NoMemTxt:	dc.b	"Not enough memory available!",10,0
ReadErrTxt:	dc.b	"Read Error!",10,0
NotCrunchedTxt:	dc.b	"Can't decrunch `%s': File is not crunched!",10,0
AlreadyCrTxt:	dc.b	"Can't crunch `%s': File is already crunched!",10,0
CrunchingTxt:	dc.b	"Crunching...",0
CrunchedTxt:	dc.b	" %ld -> %ld (%d%% gain)",10,0
AbortTxt:	dc.b	"Crunching aborted!",10,0
NotCrTxt:	dc.b	"File not crunchable!",10,0
UnknownErrTxt:	dc.b	"Strange error occurred while crunching!",10,0
SavingTxt:	dc.b	"Saving `%s' (%ld bytes)...",0
ErrorWriteTxt:	dc.b	" Error while writing!",10,0
Comment:	dc.b	"CrM!%08lx",0
DecrunchingTxt:	dc.b	"Decrunching (%ld -> %ld)...",0
DecrErrorTxt:	dc.b	" Error while decrunching!",10,0
TooLongFileTxt:	dc.b	"File not saved: crunched file is longer than original",10,0

