mirror of
https://github.com/wnayes/macutils.git
synced 2025-03-05 14:30:19 +00:00
Create macutils repository
This commit is contained in:
commit
72ea2b578a
483
README
Executable file
483
README
Executable file
@ -0,0 +1,483 @@
|
||||
This is version 2.0b3 of macutil (22-OCT-1992).
|
||||
|
||||
This package contains the following utilities:
|
||||
macunpack
|
||||
hexbin
|
||||
macsave
|
||||
macstream
|
||||
binhex
|
||||
tomac
|
||||
frommac
|
||||
|
||||
Requirements:
|
||||
a. Of course a C compiler.
|
||||
b. A 32-bit machine with large memory (or at least the ability to 'malloc'
|
||||
large chunks of memory). For reasons of efficiency and simplicity the
|
||||
programs work 'in-core', also many files are first read in core.
|
||||
If somebody can take the trouble to do it differently, go ahead!
|
||||
There are also probably in a number of places implicit assumptions that
|
||||
an int is 32 bits. If you encounter such occurrences feel free to
|
||||
notify me.
|
||||
c. A Unix (tm) machine, or something very close. There are probably quite
|
||||
a lot of Unix dependencies. Also here, if you have replacements, feel
|
||||
free to send comments.
|
||||
d. This version normally uses the 'mkdir' system call available on BSD Unix
|
||||
and some versions of SysV Unix. You can change that, see the makefile for
|
||||
details.
|
||||
|
||||
File name translation:
|
||||
|
||||
The programs use a table driven program to do Mac filename -> Unix filename
|
||||
translation. When compiled without further changes the translation is as
|
||||
follows:
|
||||
Printable ASCII characters except space and slash are not changed.
|
||||
Slash and space are changed to underscore, as are all characters that
|
||||
do not fall in the following group.
|
||||
Accented letters are translated to their unaccented counterparts.
|
||||
If your system supports the Latin-1 character set, you can change this
|
||||
translation scheme by specifying '-DLATIN1' for the 'CF' macro in the
|
||||
makefile. This will translate all accented letters (and some symbols)
|
||||
to their Latin-1 counterpart. This feature is untested (I do not have
|
||||
access to systems that cater for Latin-1), so use with care.
|
||||
Future revisions of the program will have user settable conversions.
|
||||
|
||||
Another feature of filename translation is that when the -DNODOT flag is
|
||||
specified in the CF macro an initial period will be translated to underscore.
|
||||
|
||||
MacBinary stream:
|
||||
|
||||
Most programs allow MacBinary streams as either input or output. A
|
||||
MacBinary stream is a series of files in MacBinary format pasted
|
||||
together. Embedded within a MacBinary stream can be information about
|
||||
folders. So a MacBinary stream can contain all information about a
|
||||
folder and its constituents.
|
||||
|
||||
Appleshare support:
|
||||
|
||||
Optionally the package can be compiled for systems that support the sharing
|
||||
of Unix and Mac filesystems. The package supports AUFS (AppleTalk Unix File
|
||||
Server) from CAP (Columbia AppleTalk Package) and AppleDouble (from Apple).
|
||||
It will not support both at the same time. Moreover this support requires
|
||||
the existence of the 'mkdir' system call. And finally, as implemented it
|
||||
probably will work on big-endian BSD compatible systems. If you have a SysV
|
||||
system with restricted filename lengths you can get problems. I do not know
|
||||
also whether the structures are stored native or Apple-wise on little-endian
|
||||
systems. And also, I did not test it fully; having no access to either AUFS
|
||||
or AppleDouble systems.
|
||||
|
||||
Acknowledgements:
|
||||
a. Macunpack is for a large part based on the utilities 'unpit' and 'unsit'
|
||||
written by:
|
||||
Allan G. Weber
|
||||
weber%brand.usc.edu@oberon.usc.edu
|
||||
(wondering whether that is still valid!). I combined the two into a
|
||||
single program and did a lot of modification. For information on the
|
||||
originals, see the files README.unpit and README.unsit.
|
||||
b. The crc-calculating routines are based on a routine originally written by:
|
||||
Mark G. Mendel
|
||||
UUCP: ihnp4!umn-cs!hyper!mark
|
||||
(this will not work anymore for sure!). Also here I modified the stuff
|
||||
and expanded it, see the files README.crc and README.crc.orig.
|
||||
c. LZW-decompression is taken from the sources of compress that are floating
|
||||
around. Probably I did not use the most efficient version, but this
|
||||
program was written to get it done. The version I based it on (4.0) is
|
||||
authored by:
|
||||
Steve Davies (decvax!vax135!petsd!peora!srd)
|
||||
Jim McKie (decvax!mcvax!jim) (Hi Jim!)
|
||||
Joe Orost (decvax!vax135!petsd!joe)
|
||||
Spencer W. Thomas (decvax!harpo!utah-cs!utah-gr!thomas)
|
||||
Ken Turkowski (decvax!decwrl!turtlevax!ken)
|
||||
James A. Woods (decvax!ihnp4!ames!jaw)
|
||||
I am sure those e-mail addresses also will not work!
|
||||
d. Optional AUFS support comes from information supplied by:
|
||||
Casper H.S. Dik
|
||||
University of Amsterdam
|
||||
Kruislaan 409
|
||||
1098 SJ Amsterdam
|
||||
Netherlands
|
||||
|
||||
phone: +31205922022
|
||||
email: casper@fwi.uva.nl
|
||||
This is an e-mail address that will workm but the address and phone
|
||||
number ar no longer valid.
|
||||
See the makefile.
|
||||
Some caveats are applicable:
|
||||
1. I did not fully test it (we do not use it). But the unpacking
|
||||
appears to be correct. Anyhow, as the people who initially compile
|
||||
it and use it will be system administrators I am confident they are
|
||||
able to locate bugs! (What if an archive contains a Macfile with
|
||||
the name .finderinfo or .resource? I have had two inputs for AUFS
|
||||
support [I took Caspers; his came first], but both do not deal with
|
||||
that. Does CAP deal with it?) Also I have no idea whether this
|
||||
version supports it under SysV, so beware.
|
||||
2. From one of the README's supplied by Casper:
|
||||
Files will not appear in an active folder, because Aufs doesn't like
|
||||
people working behind it's back.
|
||||
Simply opening and closing the folder will suffice.
|
||||
Appears to be the same problem as when you are unpacking or in some
|
||||
other way creating files in a folder open to multifinder. I have seen
|
||||
bundle bits disappear this way. So if after unpacking you see the
|
||||
generic icon; check whether a different icon should appear and check
|
||||
the bundle bit.
|
||||
The desktop isn't updated, but that doesn't seem to matter.
|
||||
I dunno, not using it.
|
||||
e. Man pages are now supplied. The base was provided by:
|
||||
Douglas Siebert
|
||||
ISCA
|
||||
dsiebert@icaen.uiowa.edu
|
||||
f. Because of some problems the Uncompactor has been rewritten, it is now
|
||||
based on sources from the dearchiver unzip (of PC fame). Apparently the
|
||||
base code is by:
|
||||
Samuel H. Smith
|
||||
I have no further address available, but as soon as I find a better
|
||||
attribution, I will include it.
|
||||
g. UnstuffIt's LZAH code comes from lharc (also of PC fame) by:
|
||||
Haruhiko Okumura,
|
||||
Haruyasu Yoshizaki,
|
||||
Yooichi Tagawa.
|
||||
h. Zoom's code comes from information supplied by Jon W{tte
|
||||
(d88-jwa@nada.kth.se). The Zoo decompressor is based on the routine
|
||||
written by Rahul Dhesi (dhesi@cirrus.COM). This again is based on
|
||||
code by Haruhiko Okumura. See also the file README.zoom.
|
||||
i. MacLHa's decompressors are identical to the ones mentioned in g and h.
|
||||
j. Most of hexbin's code is based on code written/modified by:
|
||||
Dave Johnson, Brown University Computer Science
|
||||
Darin Adler, TMQ Software
|
||||
Jim Budler, amdcad!jimb
|
||||
Dan LaLiberte, liberte@uiucdcs
|
||||
ahm (?)
|
||||
Jeff Meyer, John Fluke Company
|
||||
Guido van Rossum, guido@cwi.nl (Hi!)
|
||||
(most of the e-mail addresses will not work, the affiliation may also
|
||||
be incorrect by now.) See also the file README.hexbin.
|
||||
k. The dl code in hexbin comes is based on the original distribution of
|
||||
SUMacC.
|
||||
l. The mu code in hexbin is a slight modification of the hcx code (the
|
||||
compressions are identical).
|
||||
m. The MW code for StuffIt is loosely based on code by Daniel H. Bernstein
|
||||
(brnstnd@acf10.nyu.edu).
|
||||
n. Tomac and frommac are loosely based on the original macput and macget
|
||||
by (the e-mail address will not work anymore):
|
||||
Dave Johnson
|
||||
ddj%brown@csnet-relay.arpa
|
||||
Brown University Computer Science
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Macunpack will unpack PackIt, StuffIt, Diamond, Compactor/Compact Pro, most
|
||||
StuffItClassic/StuffItDeluxe, and all Zoom and LHarc/MacLHa archives, and
|
||||
archives created by later versions of DiskDoubler.
|
||||
Also it will decode files created by BinHex5.0, MacBinary, UMCP,
|
||||
Compress It, ShrinkToFit, MacCompress, DiskDoubler and AutoDoubler.
|
||||
|
||||
(PackIt, StuffIt, Diamond, Compactor, Compact/Pro, Zoom and LHarc/MacLHa are
|
||||
archivers written by respectively: Harry R. Chesley, Raymond Lau, Denis Sersa,
|
||||
Bill Goodman, Jon W{tte* and Kazuaki Ishizaki. BinHex 5.0, MacBinary and
|
||||
UMCP are by respectively: Yves Lempereur, Gregory J. Smith, Information
|
||||
Electronics. ShrinkToFit is by Roy T. Hashimoto, Compress It by Jerry
|
||||
Whitnell, and MacCompress, DiskDoubler and AutoDoubler are all by
|
||||
Lloyd Chambers.)
|
||||
|
||||
* from his signature:
|
||||
Jon W{tte - Yes, that's a brace - Damn Swede.
|
||||
Actually it is an a with two dots above; some (German inclined) people
|
||||
refer to it (incorrectly) as a-umlaut.
|
||||
|
||||
It does not deal with:
|
||||
a. Password protected archives.
|
||||
b. Multi-segment archives.
|
||||
c. Plugin methods for Zoom.
|
||||
d. MacLHa archives not packed in MacBinary mode (the program deals very
|
||||
poorly with that!).
|
||||
|
||||
Background:
|
||||
There are millions of ways to pack files, and unfortunately, all have been
|
||||
implemented one way or the other. Below I will give some background
|
||||
information about the packing schemes used by the different programs
|
||||
mentioned above. But first some background about compression (I am no
|
||||
expert, more comprehensive information can be found in for instance:
|
||||
Tomothy Bell, Ian H. Witten and John G. Cleary, Modelling for Text
|
||||
Compression, ACM Computing Surveys, Vol 21, No 4, Dec 1989, pp 557-591).
|
||||
|
||||
Huffman encoding (also called Shannon-Fano coding or some other variation
|
||||
of the name). An encoding where the length of the code for the symbols
|
||||
depends on the frequency of the symbols. Frequent symbols have shorter
|
||||
codes than infrequent symbols. The normal method is to first scan the
|
||||
file to be compressed, and to assign codes when this is done (see for
|
||||
instance: D. E. Knuth, the Art of Computer Programming). Later methods
|
||||
have been designed to create the codes adaptively; for a survey see:
|
||||
Jeremy S. Vetter, Design and Analysis of Dynamic Huffman Codes, JACM,
|
||||
Vol 34, No 4, Oct 1987, pp 825-845.
|
||||
LZ77: The first of two Ziv-Lempel methods. Using a window of past encoded
|
||||
text, output consists of triples for each sequence of newly encoded
|
||||
symbols: a back pointer and length of past text to be repeated and the
|
||||
first symbol that is not part of that sequence. Later versions allowed
|
||||
deviation from the strict alternation of pointers and uncoded symbols
|
||||
(LZSS by Bell). Later Brent included Huffman coding of the pointers
|
||||
(LZH).
|
||||
LZ78: While LZ77 uses a window of already encoded text as a dictionary,
|
||||
LZ78 dynamically builds the dictionary. Here again pointers are strictly
|
||||
alternated with unencoded new symbols. Later Welch (LZW) managed to
|
||||
eliminate the output of unencoded symbols. This algorithm is about
|
||||
the same as the one independently invented by Miller and Wegman (MW).
|
||||
A problem with these two schemes is that they are patented. Thomas
|
||||
modified LZW to LZC (as used in the Unix compress command). While LZ78
|
||||
and LZW become static once the dictionary is full, LZC has possibilities
|
||||
to reset the dictionary. Many LZC variants are in use, depending on the
|
||||
size of memory available. They are distinguished by the maximum number
|
||||
of bits that are used in a code.
|
||||
A number of other schemes are proposed and occasionally used. The main
|
||||
advantage of the LZ type schemes is that (especially) decoding is fairly fast.
|
||||
|
||||
Programs background:
|
||||
|
||||
Plain programs:
|
||||
BinHex 5.0:
|
||||
Unlike what its name suggest this is not a true successor of BinHex 4.0.
|
||||
BinHex 5.0 takes the MacBinary form of a file and stores it in the data
|
||||
fork of the newly created file.
|
||||
Although BinHex 5.0 does not create BinHex 4.0 compatible files, StuffIt
|
||||
will give the creator type of BinHex 5.0 (BnHq) to its binhexed files,
|
||||
rather than the creator type of BinHex 4.0 (BNHQ). The program knows
|
||||
about that.
|
||||
MacBinary:
|
||||
As its name suggests, it does the same as BinHex 5.0.
|
||||
UMCP:
|
||||
Looks similar, but the file as stored by UMCP is not true MacBinary.
|
||||
Size fields are modified, the result is not padded to a multiple of 128,
|
||||
etc. Macunpack deals with all that, but until now is not able to
|
||||
correctly restore the finder flags of the original file. Also, UMCP
|
||||
created files have type "TEXT" and creator "ttxt", which can create a
|
||||
bit of confusion. Macunpack will recognize these files only if the
|
||||
creator has been modified to "UMcp".
|
||||
|
||||
Compressors:
|
||||
ShrinkToFit:
|
||||
This program uses a Huffman code to compress. It has an option (default
|
||||
checked for some reason), COMP, for which I do not yet know the
|
||||
meaning. Compressing more than a single file in a single run results
|
||||
in a failure for the second and subsequent files.
|
||||
Compress It:
|
||||
Also uses a Huffman code to compress.
|
||||
MacCompress:
|
||||
MacCompress has two modes of operation, the first mode is (confusingly)
|
||||
MacCompress, the second mode is (again confusingly) UnixCompress. In
|
||||
MacCompress mode both forks are compressed using the LZC algorithm.
|
||||
In UnixCompress mode only the data fork is compressed, and some shuffling
|
||||
of resources is performed. Upto now macunpack only deals with MacCompress
|
||||
mode. The LZC variant MacCompress uses depends on memory availability.
|
||||
12 bit to 16 bit LZC can be used.
|
||||
|
||||
Archivers:
|
||||
ArcMac:
|
||||
Nearly PC-Arc compatible. Arc knows 8 compression methods, I have seen
|
||||
all of them used by ArcMac, except the LZW techniques. Here they are:
|
||||
1: No compression, shorter header
|
||||
2: No compression
|
||||
3: (packing) Run length encoding
|
||||
4: (squeezing) RLE followed by Huffman encoding
|
||||
5: (crunching) LZW
|
||||
6: (crunching) RLE followed by LZW
|
||||
7: (crunching) as the previous but with a different hash function
|
||||
8: (crunching) RLE followed by 12-bit LZC
|
||||
9: (squashing) 13-bit LZC
|
||||
PackIt:
|
||||
When archiving a file PackIt either stores the file uncompressed or
|
||||
stores the file Huffman encoded. In the latter case both forks are
|
||||
encoded using the same Huffman tree.
|
||||
StuffIt and StuffIt Classic/Deluxe:
|
||||
These have the ability to use different methods for the two forks of a
|
||||
file. The following standard methods I do know about (the last three
|
||||
are only used by the Classic/Deluxe version 2.0 of StuffIt):
|
||||
0: No compression
|
||||
1: Run length encoding
|
||||
2: 14-bit LZC compression
|
||||
3: Huffman encoding
|
||||
5: LZAH: like LZH, but the Huffman coding used is adaptive
|
||||
6: A Huffman encoding using a fixed (built-in) Huffman tree
|
||||
8: A MW encoding
|
||||
Diamond:
|
||||
Uses a LZ77 like frontend plus a Fraenkel-Klein like backend (see
|
||||
Apostolico & Galil, Combinatorial Algorithms on Words, pages 169-183).
|
||||
Compactor/Compact Pro:
|
||||
Like StuffIt, different encodings are possible for data and resource fork.
|
||||
Only two possible methods are used:
|
||||
0: Run length encoding
|
||||
1: RLE followed by some form of LZH
|
||||
Zoom:
|
||||
Data and resource fork are compressed with the same method. The standard
|
||||
uses either no compression or some form of LZH
|
||||
MacLHa:
|
||||
Has two basic modes of operation, Mac mode and Normal mode. In Mac mode
|
||||
the file is archived in MacBinary form. In normal mode only the forks
|
||||
are archived. Normal mode should not be used (and can not be unpacked
|
||||
by macunpack) as all information about data fork size/resource fork size,
|
||||
type, creator etc. is lost. It knows quite a few methods, some are
|
||||
probably only used in older versions, the only methods I have seen used
|
||||
are -lh0-, -lh1- and -lh5-. Methods known by MacLHa:
|
||||
-lz4-: No compression
|
||||
-lz5-: LZSS
|
||||
-lzs-: LZSS, another variant
|
||||
-lh0-: No compression
|
||||
-lh1-: LZAH (see StuffIt)
|
||||
-lh2-: Another form of LZAH
|
||||
-lh3-: A form of LZH, different from the next two
|
||||
-lh4-: LZH with a 4096 byte buffer (as far as I can see the coding in
|
||||
MacLHa is wrong)
|
||||
-lh5-: LZH with a 8192 byte buffer
|
||||
DiskDoubler:
|
||||
The older version of DiskDoubler is compatible with MacCompress. It does
|
||||
not create archives, it only compresses files. The newer version (since
|
||||
3.0) does both archiving and compression. The older version uses LZC as
|
||||
its compression algorithm, the newer version knows a number of different
|
||||
compression algorithms. Many (all?) are algorithms used in other
|
||||
archivers. Probably this is done to simplify conversion from other formats
|
||||
to DiskDoubler format archives. I have seen actual DiskDoubler archives
|
||||
that used methods 0, 1 and 8:
|
||||
0: No compression
|
||||
1: LZC
|
||||
2: unknown
|
||||
3: RLE
|
||||
4: Huffman (or no compression)
|
||||
5: unknown
|
||||
6: unknown
|
||||
7: An improved form of LZSS
|
||||
8: Compactor/Compact Pro compatible RLE/LZH or RLE only
|
||||
9: unknown
|
||||
The DiskDoubler archive format contains many subtle twists that make it
|
||||
difficult to properly read the archive (or perhaps this is on purpose?).
|
||||
|
||||
Naming:
|
||||
Some people have complained about the name conflict with the unpack utility
|
||||
that is already available on Sys V boxes. I had forgotten it, so there
|
||||
really was a problem. The best way to solve it was to trash pack/unpack/pcat
|
||||
and replace it by compress/uncompress/zcat. Sure, man uses it; but man uses
|
||||
pcat, so you can retain pcat. If that was not an option you were able to feel
|
||||
free to rename the program. But finally I relented. It is now macunpack.
|
||||
|
||||
When you have problems unpacking an archive feel free to ask for information.
|
||||
I am especially keen when the program detects an unknown method. If you
|
||||
encounter such an archive, please, mail a 'binhexed' copy of the archive
|
||||
to me so that I can deal with it. Password protected archives are (as
|
||||
already stated) not implemented. I do not have much inclination to do that.
|
||||
Also I feel no inclination to do multi-segment archives.
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Hexbin will de-hexify files created in BinHex 4.0 compatible format (hqx)
|
||||
but also the older format (dl, hex and hcx). Moreover it will uudecode
|
||||
files uuencoded by UUTool (the only program I know that does UU hexification
|
||||
of all Mac file information).
|
||||
|
||||
There are currently many programs that are able to create files in BinHex 4.0
|
||||
compatible format. There are however some slight differences, and most
|
||||
de-hexifiers are not able to deal with all the variations. This program is
|
||||
very simple minded. First it will intuit (based on the input) whether the
|
||||
file is in dl, hex, hcx or hqx format. Next it will de-hexify the file.
|
||||
When the format is hqx, it will check whether more files follow, and continue
|
||||
processing. So you can catenate multiple (hqx) hexified files together and
|
||||
feed them as a single file to hexbin. Also hexbin does not mind whether lines
|
||||
are separated by CR's, LF's or combinations of the two. Moreover, it will
|
||||
strip all leading, trailing and intermediate garbage introduced by mailers
|
||||
etc. Next, it does not mind if a file is not terminated by a CR or an LF
|
||||
(as StuffIt 1.5.1 and earlier did), but in that case a second file is not
|
||||
allowed to follow it. Last, while most hexifiers output lines of equal length,
|
||||
some do not. Hexbin will deal with that, but there are some caveats; see the
|
||||
-c option in the man page.
|
||||
|
||||
Background:
|
||||
|
||||
dl format:
|
||||
This was the first hexified format used. Programs to deal with it came
|
||||
from SUMacC. This format only coded resource forks, 4 bits in a byte.
|
||||
hex format:
|
||||
I think this is the first format from Yves Lempereur. Like dl format,
|
||||
it codes 4 bits in a byte, but is able to code both resource and
|
||||
data fork. Is it BinHex 2.0?
|
||||
hcx format:
|
||||
A compressing variant of hex format. Codes 6 bits in a byte.
|
||||
Is it BinHex 3.0?
|
||||
hqx format:
|
||||
Like hcx, but using a different coding (possibly to allow for ASCII->EBCDIC
|
||||
and EBCDIC->ASCII translation, which not always results in an identical
|
||||
file). Moreover this format also encodes the original Mac filename.
|
||||
mu format:
|
||||
The conversion can be done by the UUTool program from Octavian Micro
|
||||
Development. It encodes both forks and also some finder info. You will
|
||||
in general not use this with uudecode on non Mac systems, with uudecode
|
||||
only the data fork will be uudecoded. UU hexification is well known (and
|
||||
fairly old) in Unix environments. Moreover it has been ported to lots of
|
||||
other systems.
|
||||
-------------------------------------------------------------------------------
|
||||
Macsave reads a MacBinary stream from standard input and writes the
|
||||
files according to the options.
|
||||
-------------------------------------------------------------------------------
|
||||
Macstream reads files from the Unix host and will output a MacBinary stream
|
||||
containing all those files together with information about the directory
|
||||
structure.
|
||||
-------------------------------------------------------------------------------
|
||||
Binhex will read a MacBinary stream, or will read files/directories as
|
||||
indicated on the command line, and will output all files in binhexed (.hqx)
|
||||
format. Information about the directory structure is lost.
|
||||
-------------------------------------------------------------------------------
|
||||
Tomac will transmit a MacBinary stream, or named files to the Mac using
|
||||
the XMODEM protocol.
|
||||
-------------------------------------------------------------------------------
|
||||
Frommac will receive one or more files from the Mac using the XMODEM protocol.
|
||||
-------------------------------------------------------------------------------
|
||||
This is an ongoing project, more stuff will appear.
|
||||
|
||||
All comments are still welcome. Thanks for the comments I already received.
|
||||
|
||||
dik t. winter, amsterdam, nederland
|
||||
email: dik@cwi.nl
|
||||
|
||||
--
|
||||
Note:
|
||||
In these programs all algorithms are implemented based on publicly available
|
||||
software to prevent any claim that would prevent redistribution due to
|
||||
Copyright. Although parts of the code would indeed fall under the Copyright
|
||||
by the original author, use and redistribution of all such code is explicitly
|
||||
allowed. For some parts of it the GNU software license does apply.
|
||||
--
|
||||
Appendix.
|
||||
|
||||
BinHex 4.0 compatible file creators:
|
||||
|
||||
Type Creator Created by
|
||||
|
||||
"TEXT" "BthX" BinHqx
|
||||
"TEXT" "BNHQ" BinHex
|
||||
"TEXT" "BnHq" StuffIt and StuffIt Classic
|
||||
"TEXT" "ttxt" Compactor
|
||||
|
||||
Files recognized by macunpack:
|
||||
|
||||
Type Creator Recognized as
|
||||
|
||||
"APPL" "DSEA" "DiskDoubler" Self extracting
|
||||
"APPL" "EXTR" "Compactor" Self extracting
|
||||
"APPL" "Mooz" "Zoom" Self extracting
|
||||
"APPL" "Pack" "Diamond" Self extracting
|
||||
"APPL" "arc@" "ArcMac" Self extracting (not yet)
|
||||
"APPL" "aust" "StuffIt" Self extracting
|
||||
"ArCv" "TrAS" "AutoSqueeze" (not yet)
|
||||
"COMP" "STF " "ShrinkToFit"
|
||||
"DD01" "DDAP" "DiskDoubler"
|
||||
"DDAR" "DDAP" "DiskDoubler"
|
||||
"DDF." "DDAP" "DiskDoubler" (any fourth character)
|
||||
"DDf." "DDAP" "DiskDoubler" (any fourth character)
|
||||
"LARC" "LARC" "MacLHa (LHARC)"
|
||||
"LHA " "LARC" "MacLHa (LHA)"
|
||||
"PACT" "CPCT" "Compactor"
|
||||
"PIT " "PIT " "PackIt"
|
||||
"Pack" "Pack" "Diamond"
|
||||
"SIT!" "SIT!" "StuffIt"
|
||||
"SITD" "SIT!" "StuffIt Deluxe"
|
||||
"Smal" "Jdw " "Compress It"
|
||||
"TEXT" "BnHq" "BinHex 5.0"
|
||||
"TEXT" "GJBU" "MacBinary 1.0"
|
||||
"TEXT" "UMcp" "UMCP"
|
||||
"ZIVM" "LZIV" "MacCompress(M)"
|
||||
"ZIVU" "LZIV" "MacCompress(U)" (not yet)
|
||||
"mArc" "arc*" "ArcMac" (not yet)
|
||||
"zooM" "zooM" "Zoom"
|
||||
|
174
binhex/binhex.c
Executable file
174
binhex/binhex.c
Executable file
@ -0,0 +1,174 @@
|
||||
#include <stdio.h>
|
||||
#include "../fileio/machdr.h"
|
||||
#include "../fileio/rdfile.h"
|
||||
#include "../util/patchlevel.h"
|
||||
|
||||
extern char *malloc();
|
||||
extern char *realloc();
|
||||
extern char *strcat();
|
||||
extern void exit();
|
||||
extern void transname();
|
||||
extern void do_indent();
|
||||
extern void dofile();
|
||||
|
||||
#define LOCALOPT "RilqVH"
|
||||
|
||||
static void usage();
|
||||
|
||||
static char options[128];
|
||||
static char *dir_stack;
|
||||
static int dir_ptr = -64;
|
||||
static int dir_max;
|
||||
int dorep = 1;
|
||||
|
||||
int main(argc, argv)
|
||||
int argc;
|
||||
char **argv;
|
||||
{
|
||||
int c, i, j, n;
|
||||
extern int optind;
|
||||
extern char *optarg;
|
||||
int errflg;
|
||||
char text[32], ftype[5], fauth[5];
|
||||
int dir_skip = 0, write_it, query = 0, list = 0, info_only = 0;
|
||||
int indent = 0;
|
||||
|
||||
(void)strcat(options, get_rdfileopt());
|
||||
(void)strcat(options, LOCALOPT);
|
||||
errflg = 0;
|
||||
|
||||
while((c = getopt(argc, argv, options)) != EOF) {
|
||||
if(!rdfileopt((char)c)) {
|
||||
switch(c) {
|
||||
case 'R':
|
||||
dorep = 0;
|
||||
break;
|
||||
case 'l':
|
||||
list++;
|
||||
break;
|
||||
case 'q':
|
||||
query++;
|
||||
break;
|
||||
case 'i':
|
||||
info_only++;
|
||||
break;
|
||||
case '?':
|
||||
errflg++;
|
||||
break;
|
||||
case 'H':
|
||||
give_rdfileopt();
|
||||
(void)fprintf(stderr, "Binhex specific options:\n");
|
||||
(void)fprintf(stderr, "-r:\tdo not use run length encoding\n");
|
||||
(void)fprintf(stderr,
|
||||
"-i:\tgive information only, do not write\n");
|
||||
(void)fprintf(stderr, "-l:\tgive listing\n");
|
||||
(void)fprintf(stderr,
|
||||
"-q:\tquery for every file/folder before writing\n");
|
||||
(void)fprintf(stderr,
|
||||
"-V:\tgive information about this version\n");
|
||||
(void)fprintf(stderr, "-H:\tthis message\n");
|
||||
(void)fprintf(stderr, "Default is silent writing\n");
|
||||
exit(0);
|
||||
case 'V':
|
||||
(void)fprintf(stderr, "Version %s, ", VERSION);
|
||||
(void)fprintf(stderr, "patchlevel %d", PATCHLEVEL);
|
||||
(void)fprintf(stderr, "%s.\n", get_minb());
|
||||
exit(0);
|
||||
}
|
||||
}
|
||||
}
|
||||
if(errflg) {
|
||||
usage();
|
||||
exit(1);
|
||||
}
|
||||
|
||||
if(info_only || query) {
|
||||
list++;
|
||||
}
|
||||
|
||||
setup(argc - optind, argv + optind);
|
||||
while((i = nextfile()) != ISATEND) {
|
||||
if(dir_skip) {
|
||||
if(i == ISDIR) {
|
||||
dir_skip++;
|
||||
} else if(i == ENDDIR) {
|
||||
dir_skip--;
|
||||
}
|
||||
continue;
|
||||
}
|
||||
|
||||
write_it = 1;
|
||||
n = file_info[I_NAMEOFF] & 0x7f;
|
||||
transname(file_info + I_NAMEOFF + 1, text, n);
|
||||
if(i == ISFILE) {
|
||||
transname(file_info + I_TYPEOFF, ftype, 4);
|
||||
transname(file_info + I_AUTHOFF, fauth, 4);
|
||||
}
|
||||
if(list) {
|
||||
if(i == ISFILE) {
|
||||
do_indent(indent);
|
||||
(void)fprintf(stderr,
|
||||
"name=\"%s\", type=%4.4s, author=%4.4s, data=%ld, rsrc=%ld",
|
||||
text, ftype, fauth, (long)data_size, (long)rsrc_size);
|
||||
} else if(i == ISDIR) {
|
||||
do_indent(indent);
|
||||
dir_ptr += 64;
|
||||
if(dir_ptr == dir_max) {
|
||||
if(dir_max == 0) {
|
||||
dir_stack = malloc(64);
|
||||
} else {
|
||||
dir_stack = realloc(dir_stack, (unsigned)dir_max + 64);
|
||||
}
|
||||
dir_max += 64;
|
||||
if(dir_stack == NULL) {
|
||||
(void)fprintf(stderr, "Insufficient memory\n");
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
for(j = 0; j <= n; j++) {
|
||||
dir_stack[dir_ptr + j] = text[j];
|
||||
}
|
||||
(void)fprintf(stderr, "folder=\"%s\"", text);
|
||||
indent++;
|
||||
} else {
|
||||
indent--;
|
||||
do_indent(indent);
|
||||
(void)fprintf(stderr, "leaving folder \"%s\"",
|
||||
dir_stack + dir_ptr);
|
||||
dir_ptr -= 64;
|
||||
}
|
||||
if(info_only) {
|
||||
write_it = 0;
|
||||
}
|
||||
if(query) {
|
||||
if(i != ENDDIR) {
|
||||
write_it = do_query();
|
||||
} else {
|
||||
(void)fputc('\n', stderr);
|
||||
}
|
||||
if(!write_it && i == ISDIR) {
|
||||
dir_skip = 1;
|
||||
indent--;
|
||||
dir_ptr -= 64;
|
||||
}
|
||||
} else {
|
||||
(void)fputc('\n', stderr);
|
||||
}
|
||||
}
|
||||
|
||||
if(write_it) {
|
||||
if(i == ISFILE) {
|
||||
dofile();
|
||||
}
|
||||
}
|
||||
}
|
||||
exit(0);
|
||||
/* NOTREACHED */
|
||||
}
|
||||
|
||||
static void usage()
|
||||
{
|
||||
(void)fprintf(stderr, "Usage: binhex [-%s] [files]\n", options);
|
||||
(void)fprintf(stderr, "Use \"binhex -H\" for help.\n");
|
||||
}
|
||||
|
192
binhex/dofile.c
Executable file
192
binhex/dofile.c
Executable file
@ -0,0 +1,192 @@
|
||||
#include "../fileio/machdr.h"
|
||||
#include "../fileio/rdfile.h"
|
||||
|
||||
extern int dorep;
|
||||
extern unsigned long binhex_crcinit;
|
||||
extern unsigned long binhex_updcrc();
|
||||
|
||||
#define RUNCHAR 0x90
|
||||
|
||||
static int pos_ptr;
|
||||
static char codes[] =
|
||||
"!\"#$%&'()*+,-012345689@ABCDEFGHIJKLMNPQRSTUVXYZ[`abcdefhijklmpqr";
|
||||
static int state;
|
||||
static int savebits;
|
||||
static int rep_char;
|
||||
static int rep_count;
|
||||
|
||||
void doheader();
|
||||
void dofork();
|
||||
void outbyte();
|
||||
void finish();
|
||||
void outbyte1();
|
||||
void out6bit();
|
||||
void outchar();
|
||||
|
||||
void dofile()
|
||||
{
|
||||
(void)printf("(This file must be converted; you knew that already.)\n");
|
||||
(void)printf("\n");
|
||||
pos_ptr = 1;
|
||||
state = 0;
|
||||
rep_char = -1;
|
||||
rep_count = 0;
|
||||
outchar(':');
|
||||
doheader();
|
||||
dofork(data_fork, data_size);
|
||||
dofork(rsrc_fork, rsrc_size);
|
||||
finish();
|
||||
(void)putchar(':');
|
||||
(void)putchar('\n');
|
||||
}
|
||||
|
||||
void doheader()
|
||||
{
|
||||
unsigned long crc;
|
||||
int i, n;
|
||||
|
||||
crc = binhex_crcinit;
|
||||
n = file_info[I_NAMEOFF];
|
||||
crc = binhex_updcrc(crc, file_info + I_NAMEOFF, n + 1);
|
||||
for(i = 0; i <= n; i++) {
|
||||
outbyte(file_info[I_NAMEOFF + i]);
|
||||
}
|
||||
n = 0;
|
||||
crc = binhex_updcrc(crc, (char *)&n, 1);
|
||||
outbyte(0);
|
||||
crc = binhex_updcrc(crc, file_info + I_TYPEOFF, 4);
|
||||
for(i = 0; i < 4; i++) {
|
||||
outbyte(file_info[I_TYPEOFF + i]);
|
||||
}
|
||||
crc = binhex_updcrc(crc, file_info + I_AUTHOFF, 4);
|
||||
for(i = 0; i < 4; i++) {
|
||||
outbyte(file_info[I_AUTHOFF + i]);
|
||||
}
|
||||
crc = binhex_updcrc(crc, file_info + I_FLAGOFF, 2);
|
||||
for(i = 0; i < 2; i++) {
|
||||
outbyte(file_info[I_FLAGOFF + i]);
|
||||
}
|
||||
crc = binhex_updcrc(crc, file_info + I_DLENOFF, 4);
|
||||
for(i = 0; i < 4; i++) {
|
||||
outbyte(file_info[I_DLENOFF + i]);
|
||||
}
|
||||
crc = binhex_updcrc(crc, file_info + I_RLENOFF, 4);
|
||||
for(i = 0; i < 4; i++) {
|
||||
outbyte(file_info[I_RLENOFF + i]);
|
||||
}
|
||||
outbyte((int)(crc >> 8));
|
||||
outbyte((int)(crc & 0xff));
|
||||
}
|
||||
|
||||
void dofork(fork, size)
|
||||
char *fork;
|
||||
int size;
|
||||
{
|
||||
unsigned long crc;
|
||||
int i;
|
||||
|
||||
crc = binhex_updcrc(binhex_crcinit, fork, size);
|
||||
for(i = 0; i < size; i++) {
|
||||
outbyte(fork[i]);
|
||||
}
|
||||
outbyte((int)(crc >> 8));
|
||||
outbyte((int)(crc & 0xff));
|
||||
}
|
||||
|
||||
void outbyte(b)
|
||||
int b;
|
||||
{
|
||||
b &= 0xff;
|
||||
if(dorep && (b == rep_char)) {
|
||||
if(++rep_count == 254) {
|
||||
outbyte1(RUNCHAR);
|
||||
outbyte1(255);
|
||||
rep_char = -1;
|
||||
rep_count = 0;
|
||||
}
|
||||
} else {
|
||||
if(rep_count > 0) {
|
||||
if(rep_count > 3) {
|
||||
outbyte1(RUNCHAR);
|
||||
outbyte1(rep_count + 1);
|
||||
} else {
|
||||
while(rep_count-- > 0) {
|
||||
outbyte1(rep_char);
|
||||
}
|
||||
}
|
||||
}
|
||||
outbyte1(b);
|
||||
if(b == RUNCHAR) {
|
||||
outbyte1(0);
|
||||
rep_char = -1;
|
||||
} else {
|
||||
rep_char = b;
|
||||
}
|
||||
rep_count = 0;
|
||||
}
|
||||
}
|
||||
|
||||
void finish()
|
||||
{
|
||||
if(rep_count > 0) {
|
||||
if(rep_count > 3) {
|
||||
outbyte1(RUNCHAR);
|
||||
outbyte1(rep_count + 1);
|
||||
} else {
|
||||
while(rep_count-- > 0) {
|
||||
outbyte1(rep_char);
|
||||
}
|
||||
}
|
||||
}
|
||||
switch(state) {
|
||||
case 1:
|
||||
out6bit(savebits << 4);
|
||||
break;
|
||||
case 2:
|
||||
out6bit(savebits << 2);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void outbyte1(b)
|
||||
int b;
|
||||
{
|
||||
switch(state) {
|
||||
case 0:
|
||||
out6bit(b >> 2);
|
||||
savebits = b & 0x3;
|
||||
state = 1;
|
||||
break;
|
||||
case 1:
|
||||
b |= (savebits << 8);
|
||||
out6bit(b >> 4);
|
||||
savebits = b & 0xf;
|
||||
state = 2;
|
||||
break;
|
||||
case 2:
|
||||
b |= (savebits << 8);
|
||||
out6bit(b >> 6);
|
||||
out6bit(b & 0x3f);
|
||||
state = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void out6bit(c)
|
||||
char c;
|
||||
{
|
||||
outchar(codes[c & 0x3f]);
|
||||
}
|
||||
|
||||
void outchar(c)
|
||||
char c;
|
||||
{
|
||||
(void)putchar(c);
|
||||
if(++pos_ptr > 64) {
|
||||
(void)putchar('\n');
|
||||
pos_ptr = 1;
|
||||
}
|
||||
}
|
||||
|
51
binhex/makefile
Executable file
51
binhex/makefile
Executable file
@ -0,0 +1,51 @@
|
||||
CFLAGS = -O $(CF)
|
||||
|
||||
SRCS = binhex.c dofile.c
|
||||
|
||||
OBJS = binhex.o dofile.o
|
||||
|
||||
LIB = ../crc/libcrc.a
|
||||
TNAME = ../util/transname
|
||||
BNAME = ../util/backtrans
|
||||
UNAME = ../util/util
|
||||
INAME = ../fileio/rdfile
|
||||
GNAME = ../fileio/fileglob
|
||||
XOBJS = $(TNAME).o $(BNAME).o $(UNAME).o $(INAME).o $(GNAME).o
|
||||
XSRCS = $(TNAME).c $(BNAME).c $(UNAME).c $(INAME).c $(GNAME).c
|
||||
|
||||
binhex: $(OBJS) $(XOBJS) $(LIB)
|
||||
$(CC) $(CFLAGS) -o binhex $(OBJS) $(XOBJS) $(LIB)
|
||||
|
||||
$(LIB): ../crc/makecrc.c
|
||||
(cd ../crc; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
$(TNAME).o: $(TNAME).c
|
||||
(cd ../util; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
$(BNAME).o: $(BNAME).c
|
||||
(cd ../util; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
$(UNAME).o: $(UNAME).c
|
||||
(cd ../util; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
$(INAME).o: $(INAME).c
|
||||
(cd ../fileio; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
$(GNAME).o: $(GNAME).c
|
||||
(cd ../fileio; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
lint:
|
||||
lint $(CF) $(LFLAGS) $(SRCS) $(XSRCS)
|
||||
|
||||
clean:
|
||||
-rm -f *.o
|
||||
|
||||
clobber:clean
|
||||
-rm -f binhex
|
||||
|
||||
binhex.o: ../fileio/machdr.h
|
||||
binhex.o: ../fileio/rdfile.h
|
||||
binhex.o: ../util/patchlevel.h
|
||||
dofile.o: ../fileio/machdr.h
|
||||
dofile.o: ../fileio/rdfile.h
|
||||
|
4
comm/comm.h
Executable file
4
comm/comm.h
Executable file
@ -0,0 +1,4 @@
|
||||
#define XM /* Know about XMODEM */
|
||||
#undef YM /* Know about YMODEM */
|
||||
#undef ZM /* Know about ZMODEM */
|
||||
|
167
comm/frommac.c
Executable file
167
comm/frommac.c
Executable file
@ -0,0 +1,167 @@
|
||||
#include <stdio.h>
|
||||
#include "comm.h"
|
||||
#include "../util/patchlevel.h"
|
||||
#include "../fileio/machdr.h"
|
||||
#include "globals.h"
|
||||
#include "../fileio/fileglob.h"
|
||||
#include "../fileio/wrfile.h"
|
||||
|
||||
#define LOCALOPT "lmxyzoTVH"
|
||||
|
||||
extern void exit();
|
||||
extern void setup_tty();
|
||||
extern void reset_tty();
|
||||
|
||||
extern char info[];
|
||||
|
||||
static void usage();
|
||||
|
||||
static char options[128];
|
||||
static int multi_file = 0;
|
||||
static int listmode = 0;
|
||||
|
||||
int main(argc, argv)
|
||||
int argc;
|
||||
char **argv;
|
||||
{
|
||||
extern int optind;
|
||||
extern char *optarg;
|
||||
int errflg;
|
||||
int c;
|
||||
char tname[64];
|
||||
char fauth[5];
|
||||
char ftype[5];
|
||||
|
||||
set_wrfileopt(0);
|
||||
(void)strcat(options, get_wrfileopt());
|
||||
(void)strcat(options, LOCALOPT);
|
||||
errflg = 0;
|
||||
|
||||
while((c = getopt(argc, argv, options)) != EOF) {
|
||||
if(!wrfileopt((char)c)) {
|
||||
switch(c) {
|
||||
case 'l':
|
||||
listmode++;
|
||||
break;
|
||||
case 'm':
|
||||
multi_file++;
|
||||
break;
|
||||
case 'x':
|
||||
xfertype = XMODEM;
|
||||
#ifndef XM
|
||||
(void)fprintf(stderr, "XMODEM not supported\n");
|
||||
exit(1);
|
||||
#else /* XM */
|
||||
break;
|
||||
#endif /* XM */
|
||||
case 'y':
|
||||
xfertype = YMODEM;
|
||||
#ifndef YM
|
||||
(void)fprintf(stderr, "YMODEM not supported\n");
|
||||
exit(1);
|
||||
#else /* YM */
|
||||
break;
|
||||
#endif /* YM */
|
||||
case 'z':
|
||||
xfertype = ZMODEM;
|
||||
#ifndef ZM
|
||||
(void)fprintf(stderr, "ZMODEM not supported\n");
|
||||
exit(1);
|
||||
#else /* ZM */
|
||||
break;
|
||||
#endif /* ZM */
|
||||
case 'o':
|
||||
pre_beta++;
|
||||
break;
|
||||
case 'T':
|
||||
time_out++;
|
||||
break;
|
||||
case '?':
|
||||
errflg++;
|
||||
break;
|
||||
case 'H':
|
||||
give_wrfileopt();
|
||||
(void)fprintf(stderr, "Frommac specific options:\n");
|
||||
(void)fprintf(stderr, "-l:\tgive listing\n");
|
||||
(void)fprintf(stderr, "-m:\tmulti-file transfer\n");
|
||||
#ifdef XM
|
||||
(void)fprintf(stderr, "-x:\tuse XMODEM protocol\n");
|
||||
#endif /* XM */
|
||||
#ifdef YM
|
||||
(void)fprintf(stderr, "-y:\tuse YMODEM protocol\n");
|
||||
#endif /* YM */
|
||||
#ifdef ZM
|
||||
(void)fprintf(stderr, "-z:\tuse ZMODEM protocol\n");
|
||||
#endif /* ZM */
|
||||
(void)fprintf(stderr, "-o:\tuse pre-beta protocol\n");
|
||||
(void)fprintf(stderr, "-T:\tdetect time-outs\n");
|
||||
(void)fprintf(stderr,
|
||||
"-V:\tgive information about this version\n");
|
||||
(void)fprintf(stderr, "-H:\tthis message\n");
|
||||
(void)fprintf(stderr,
|
||||
"Default is silent receival of a single file using XMODEM\n");
|
||||
exit(0);
|
||||
case 'V':
|
||||
(void)fprintf(stderr, "Version %s, ", VERSION);
|
||||
(void)fprintf(stderr, "patchlevel %d", PATCHLEVEL);
|
||||
(void)fprintf(stderr, "%s.\n", get_mina());
|
||||
(void)fprintf(stderr, "Supported protocols:\n");
|
||||
#ifdef XM
|
||||
(void)fprintf(stderr, "\tXMODEM\n");
|
||||
#endif /* XM */
|
||||
#ifdef YM
|
||||
(void)fprintf(stderr, "\tYMODEM\n");
|
||||
#endif /* YM */
|
||||
#ifdef ZM
|
||||
(void)fprintf(stderr, "\tZMODEM\n");
|
||||
#endif /* ZM */
|
||||
exit(0);
|
||||
}
|
||||
}
|
||||
}
|
||||
if(errflg) {
|
||||
usage();
|
||||
exit(1);
|
||||
}
|
||||
|
||||
do {
|
||||
setup_tty();
|
||||
switch(xfertype) {
|
||||
case XMODEM:
|
||||
#ifdef XM
|
||||
xm_from();
|
||||
break;
|
||||
#endif /* XM */
|
||||
#ifdef YM
|
||||
case YMODEM:
|
||||
ym_from();
|
||||
break;
|
||||
#endif /* YM */
|
||||
#ifdef ZM
|
||||
case ZMODEM:
|
||||
zm_from();
|
||||
break;
|
||||
#endif /* ZM */
|
||||
}
|
||||
reset_tty();
|
||||
if(listmode) {
|
||||
transname(info + I_NAMEOFF + 1, tname, info[I_NAMEOFF]);
|
||||
transname(info + I_AUTHOFF, fauth, 4);
|
||||
transname(info + I_TYPEOFF, ftype, 4);
|
||||
(void)fprintf(stderr,
|
||||
"name=\"%s\", type=%4.4s, author=%4.4s, data=%ld, rsrc=%ld",
|
||||
tname, ftype, fauth,
|
||||
get4(info + I_DLENOFF), get4(info + I_RLENOFF));
|
||||
(void)fprintf(stderr, "\n");
|
||||
}
|
||||
} while(multi_file);
|
||||
exit(0);
|
||||
/* NOTREACHED */
|
||||
}
|
||||
|
||||
static void usage()
|
||||
{
|
||||
(void)fprintf(stderr, "Usage: frommac [-%s]\n", options);
|
||||
(void)fprintf(stderr, "Use \"frommac -H\" for help.\n");
|
||||
}
|
||||
|
6
comm/globals.c
Executable file
6
comm/globals.c
Executable file
@ -0,0 +1,6 @@
|
||||
#include "globals.h"
|
||||
|
||||
int xfertype = XMODEM;
|
||||
int pre_beta = 0;
|
||||
int time_out = 0;
|
||||
|
8
comm/globals.h
Executable file
8
comm/globals.h
Executable file
@ -0,0 +1,8 @@
|
||||
#define XMODEM 0
|
||||
#define YMODEM 1
|
||||
#define ZMODEM 2
|
||||
|
||||
extern int xfertype;
|
||||
extern int pre_beta;
|
||||
extern int time_out;
|
||||
|
91
comm/makefile
Executable file
91
comm/makefile
Executable file
@ -0,0 +1,91 @@
|
||||
CFLAGS = -O $(CF)
|
||||
|
||||
SRCS1 = tomac.c xm_to.c ym_to.c zm_to.c tty.c globals.c
|
||||
SRCS2 = frommac.c xm_from.c ym_from.c zm_from.c tty.c globals.c
|
||||
|
||||
OBJS1 = tomac.o xm_to.o ym_to.o zm_to.o tty.o globals.o
|
||||
OBJS2 = frommac.o xm_from.o ym_from.o zm_from.o tty.o globals.o
|
||||
|
||||
LIB = ../crc/libcrc.a
|
||||
TNAME = ../util/transname
|
||||
BNAME = ../util/backtrans
|
||||
UNAME = ../util/util
|
||||
INAME = ../fileio/rdfile
|
||||
ONAME = ../fileio/wrfile
|
||||
GNAME = ../fileio/fileglob
|
||||
XOBJS1 = $(TNAME).o $(BNAME).o $(UNAME).o $(INAME).o $(GNAME).o
|
||||
XOBJS2 = $(TNAME).o $(UNAME).o $(ONAME).o $(GNAME).o
|
||||
XSRCS1 = $(TNAME).c $(BNAME).c $(UNAME).c $(INAME).c $(GNAME).c
|
||||
XSRCS2 = $(TNAME).c $(UNAME).c $(ONAME).c $(GNAME).c
|
||||
|
||||
all: tomac frommac
|
||||
touch all
|
||||
|
||||
tomac: $(OBJS1) $(XOBJS1)
|
||||
$(CC) $(CFLAGS) -o tomac $(OBJS1) $(XOBJS1)
|
||||
|
||||
frommac: $(OBJS2) $(XOBJS2)
|
||||
$(CC) $(CFLAGS) -o frommac $(OBJS2) $(XOBJS2)
|
||||
|
||||
$(LIB): ../crc/makecrc.c
|
||||
(cd ../crc; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
$(TNAME).o: $(TNAME).c
|
||||
(cd ../util; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
$(BNAME).o: $(BNAME).c
|
||||
(cd ../util; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
$(UNAME).o: $(UNAME).c
|
||||
(cd ../util; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
$(INAME).o: $(INAME).c
|
||||
(cd ../fileio; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
$(ONAME).o: $(ONAME).c
|
||||
(cd ../fileio; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
$(GNAME).o: $(GNAME).c
|
||||
(cd ../fileio; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
lint:
|
||||
lint $(CF) $(LFLAGS) $(SRCS1) $(XSRCS)
|
||||
|
||||
clean:
|
||||
-rm -f *.o
|
||||
|
||||
clobber:clean
|
||||
-rm -f all tomac frommac
|
||||
|
||||
tomac.o: comm.h
|
||||
tomac.o: ../fileio/machdr.h
|
||||
tomac.o: ../fileio/rdfile.h
|
||||
tomac.o: ../util/patchlevel.h
|
||||
tomac.o: globals.h
|
||||
xm_to.o: comm.h
|
||||
xm_to.o: ../fileio/machdr.h
|
||||
xm_to.o: ../fileio/rdfile.h
|
||||
xm_to.o: ../util/masks.h
|
||||
xm_to.o: globals.h
|
||||
xm_to.o: protocol.h
|
||||
ym_to.o: comm.h
|
||||
zm_to.o: comm.h
|
||||
frommac.o: comm.h
|
||||
frommac.o: ../util/patchlevel.h
|
||||
frommac.o: ../fileio/machdr.h
|
||||
frommac.o: globals.h
|
||||
frommac.o: ../fileio/fileglob.h
|
||||
frommac.o: ../fileio/wrfile.h
|
||||
xm_from.o: comm.h
|
||||
xm_from.o: ../fileio/machdr.h
|
||||
xm_from.o: ../fileio/wrfile.h
|
||||
xm_from.o: ../util/masks.h
|
||||
xm_from.o: globals.h
|
||||
xm_from.o: protocol.h
|
||||
ym_from.o: comm.h
|
||||
zm_from.o: comm.h
|
||||
globals.o: globals.h
|
||||
tty.o: ../util/masks.h
|
||||
tty.o: protocol.h
|
||||
tty.o: globals.h
|
||||
|
22
comm/protocol.h
Executable file
22
comm/protocol.h
Executable file
@ -0,0 +1,22 @@
|
||||
#define RECORDBYTES 132
|
||||
#define DATABYTES 128
|
||||
#define NAMEBYTES 63
|
||||
|
||||
#define RETRIES 10
|
||||
#define SOHTIMO 10
|
||||
#define ACKTIMO 10
|
||||
#define LINTIMO 20
|
||||
#define CHRTIMO 2
|
||||
|
||||
#define MAXRECNO 0xff
|
||||
|
||||
#define TMO -1
|
||||
#define DUP '\000'
|
||||
#define SOH '\001'
|
||||
#define EOT '\004'
|
||||
#define ACK '\006'
|
||||
#define NAK '\025'
|
||||
#define CAN '\030'
|
||||
#define EEF '\032'
|
||||
#define ESC '\033'
|
||||
|
242
comm/tomac.c
Executable file
242
comm/tomac.c
Executable file
@ -0,0 +1,242 @@
|
||||
#include <stdio.h>
|
||||
#include "comm.h"
|
||||
#include "../fileio/machdr.h"
|
||||
#include "../fileio/rdfile.h"
|
||||
#include "../util/patchlevel.h"
|
||||
#include "globals.h"
|
||||
|
||||
extern char *malloc();
|
||||
extern char *realloc();
|
||||
extern char *strcat();
|
||||
extern void exit();
|
||||
extern void transname();
|
||||
extern void do_indent();
|
||||
extern void dofile();
|
||||
extern void setup_tty();
|
||||
extern void reset_tty();
|
||||
|
||||
#define LOCALOPT "ilqxyzoTVH"
|
||||
|
||||
static void usage();
|
||||
|
||||
static char options[128];
|
||||
static char *dir_stack;
|
||||
static int dir_ptr = -64;
|
||||
static int dir_max;
|
||||
|
||||
int main(argc, argv)
|
||||
int argc;
|
||||
char **argv;
|
||||
{
|
||||
int c, i, j, n;
|
||||
extern int optind;
|
||||
extern char *optarg;
|
||||
int errflg;
|
||||
char text[32], ftype[5], fauth[5];
|
||||
int dir_skip = 0, write_it, query = 0, list = 0, info_only = 0;
|
||||
int indent = 0;
|
||||
|
||||
(void)strcat(options, get_rdfileopt());
|
||||
(void)strcat(options, LOCALOPT);
|
||||
errflg = 0;
|
||||
|
||||
while((c = getopt(argc, argv, options)) != EOF) {
|
||||
if(!rdfileopt((char)c)) {
|
||||
switch(c) {
|
||||
case 'l':
|
||||
list++;
|
||||
break;
|
||||
case 'q':
|
||||
query++;
|
||||
break;
|
||||
case 'i':
|
||||
info_only++;
|
||||
break;
|
||||
case 'o':
|
||||
pre_beta++;
|
||||
case 'x':
|
||||
xfertype = XMODEM;
|
||||
#ifndef XM
|
||||
(void)fprintf(stderr, "XMODEM not supported\n");
|
||||
exit(1);
|
||||
#else /* XM */
|
||||
break;
|
||||
#endif /* XM */
|
||||
case 'y':
|
||||
xfertype = YMODEM;
|
||||
#ifndef YM
|
||||
(void)fprintf(stderr, "YMODEM not supported\n");
|
||||
exit(1);
|
||||
#else /* YM */
|
||||
break;
|
||||
#endif /* YM */
|
||||
case 'z':
|
||||
xfertype = ZMODEM;
|
||||
#ifndef ZM
|
||||
(void)fprintf(stderr, "ZMODEM not supported\n");
|
||||
exit(1);
|
||||
#else /* ZM */
|
||||
break;
|
||||
#endif /* ZM */
|
||||
case 'T':
|
||||
time_out++;
|
||||
break;
|
||||
case '?':
|
||||
errflg++;
|
||||
break;
|
||||
case 'H':
|
||||
give_rdfileopt();
|
||||
(void)fprintf(stderr, "Tomac specific options:\n");
|
||||
(void)fprintf(stderr,
|
||||
"-i:\tgive information only, do not write\n");
|
||||
(void)fprintf(stderr, "-l:\tgive listing\n");
|
||||
(void)fprintf(stderr,
|
||||
"-q:\tquery for every file/folder before writing\n");
|
||||
#ifdef XM
|
||||
(void)fprintf(stderr, "-x:\tuse XMODEM protocol\n");
|
||||
#endif /* XM */
|
||||
#ifdef YM
|
||||
(void)fprintf(stderr, "-y:\tuse YMODEM protocol\n");
|
||||
#endif /* YM */
|
||||
#ifdef ZM
|
||||
(void)fprintf(stderr, "-z:\tuse ZMODEM protocol\n");
|
||||
#endif /* ZM */
|
||||
(void)fprintf(stderr, "-o:\tuse pre-beta protocol\n");
|
||||
(void)fprintf(stderr, "-T:\tdetect time-outs\n");
|
||||
(void)fprintf(stderr,
|
||||
"-V:\tgive information about this version\n");
|
||||
(void)fprintf(stderr, "-H:\tthis message\n");
|
||||
(void)fprintf(stderr,
|
||||
"Default is silent sending with XMODEM\n");
|
||||
exit(0);
|
||||
case 'V':
|
||||
(void)fprintf(stderr, "Version %s, ", VERSION);
|
||||
(void)fprintf(stderr, "patchlevel %d", PATCHLEVEL);
|
||||
(void)fprintf(stderr, "%s.\n", get_minb());
|
||||
(void)fprintf(stderr, "Supported protocols:\n");
|
||||
#ifdef XM
|
||||
(void)fprintf(stderr, "\tXMODEM\n");
|
||||
#endif /* XM */
|
||||
#ifdef YM
|
||||
(void)fprintf(stderr, "\tYMODEM\n");
|
||||
#endif /* YM */
|
||||
#ifdef ZM
|
||||
(void)fprintf(stderr, "\tZMODEM\n");
|
||||
#endif /* ZM */
|
||||
exit(0);
|
||||
}
|
||||
}
|
||||
}
|
||||
if(errflg) {
|
||||
usage();
|
||||
exit(1);
|
||||
}
|
||||
|
||||
if(info_only || query) {
|
||||
list++;
|
||||
}
|
||||
|
||||
setup(argc - optind, argv + optind);
|
||||
while((i = nextfile()) != ISATEND) {
|
||||
if(dir_skip) {
|
||||
if(i == ISDIR) {
|
||||
dir_skip++;
|
||||
} else if(i == ENDDIR) {
|
||||
dir_skip--;
|
||||
}
|
||||
continue;
|
||||
}
|
||||
|
||||
write_it = 1;
|
||||
n = file_info[I_NAMEOFF] & 0x7f;
|
||||
transname(file_info + I_NAMEOFF + 1, text, n);
|
||||
if(i == ISFILE) {
|
||||
transname(file_info + I_TYPEOFF, ftype, 4);
|
||||
transname(file_info + I_AUTHOFF, fauth, 4);
|
||||
}
|
||||
if(list) {
|
||||
if(i == ISFILE) {
|
||||
do_indent(indent);
|
||||
(void)fprintf(stderr,
|
||||
"name=\"%s\", type=%4.4s, author=%4.4s, data=%ld, rsrc=%ld",
|
||||
text, ftype, fauth, (long)data_size, (long)rsrc_size);
|
||||
} else if(i == ISDIR) {
|
||||
do_indent(indent);
|
||||
dir_ptr += 64;
|
||||
if(dir_ptr == dir_max) {
|
||||
if(dir_max == 0) {
|
||||
dir_stack = malloc(64);
|
||||
} else {
|
||||
dir_stack = realloc(dir_stack, (unsigned)dir_max + 64);
|
||||
}
|
||||
dir_max += 64;
|
||||
if(dir_stack == NULL) {
|
||||
(void)fprintf(stderr, "Insufficient memory\n");
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
for(j = 0; j <= n; j++) {
|
||||
dir_stack[dir_ptr + j] = text[j];
|
||||
}
|
||||
(void)fprintf(stderr, "folder=\"%s\"", text);
|
||||
indent++;
|
||||
} else {
|
||||
indent--;
|
||||
do_indent(indent);
|
||||
(void)fprintf(stderr, "leaving folder \"%s\"",
|
||||
dir_stack + dir_ptr);
|
||||
dir_ptr -= 64;
|
||||
}
|
||||
if(info_only) {
|
||||
write_it = 0;
|
||||
}
|
||||
if(query) {
|
||||
if(i != ENDDIR) {
|
||||
write_it = do_query();
|
||||
} else {
|
||||
(void)fputc('\n', stderr);
|
||||
}
|
||||
if(!write_it && i == ISDIR) {
|
||||
dir_skip = 1;
|
||||
indent--;
|
||||
dir_ptr -= 64;
|
||||
}
|
||||
} else {
|
||||
(void)fputc('\n', stderr);
|
||||
}
|
||||
}
|
||||
|
||||
if(write_it) {
|
||||
if(i == ISFILE) {
|
||||
setup_tty();
|
||||
switch(xfertype) {
|
||||
#ifdef XM
|
||||
case XMODEM:
|
||||
xm_to();
|
||||
break;
|
||||
#endif /* XM */
|
||||
#ifdef YM
|
||||
case YMODEM:
|
||||
ym_to();
|
||||
break;
|
||||
#endif /* YM */
|
||||
#ifdef ZM
|
||||
case ZMODEM:
|
||||
zm_to();
|
||||
break;
|
||||
#endif /* ZM */
|
||||
}
|
||||
reset_tty();
|
||||
}
|
||||
}
|
||||
}
|
||||
exit(0);
|
||||
/* NOTREACHED */
|
||||
}
|
||||
|
||||
static void usage()
|
||||
{
|
||||
(void)fprintf(stderr, "Usage: tomac [-%s] [files]\n", options);
|
||||
(void)fprintf(stderr, "Use \"tomac -H\" for help.\n");
|
||||
}
|
||||
|
146
comm/tty.c
Executable file
146
comm/tty.c
Executable file
@ -0,0 +1,146 @@
|
||||
#include <stdio.h>
|
||||
#include <signal.h>
|
||||
#ifndef TERMIOS_H
|
||||
#include <sgtty.h>
|
||||
#else /* TERMIOS_H */
|
||||
#include <termios.h>
|
||||
#endif /* TERMIOS_H */
|
||||
#include <setjmp.h>
|
||||
#include "../util/masks.h"
|
||||
#include "protocol.h"
|
||||
#include "globals.h"
|
||||
|
||||
void cleanup();
|
||||
void timedout();
|
||||
int tgetc();
|
||||
void tputc();
|
||||
|
||||
static jmp_buf timobuf;
|
||||
|
||||
#ifndef TERMIOS_H
|
||||
static struct sgttyb otty, ntty;
|
||||
#else /* TERMIOS_H */
|
||||
static struct termios otty, ntty;
|
||||
#endif /* TERMIOS_H */
|
||||
static int ttyfd;
|
||||
static int signal_set;
|
||||
|
||||
void setup_tty()
|
||||
{
|
||||
ttyfd = fileno(stderr);
|
||||
if(!signal_set) {
|
||||
(void)signal(SIGHUP, cleanup);
|
||||
(void)signal(SIGINT, cleanup);
|
||||
(void)signal(SIGQUIT, cleanup);
|
||||
(void)signal(SIGTERM, cleanup);
|
||||
if(time_out) {
|
||||
(void)signal(SIGALRM, timedout);
|
||||
}
|
||||
signal_set = 1;
|
||||
}
|
||||
#ifndef TERMIOS_H
|
||||
(void)ioctl(ttyfd, TIOCGETP, &otty);
|
||||
ntty = otty;
|
||||
ntty.sg_flags = RAW | ANYP;
|
||||
(void)ioctl(ttyfd, TIOCSETP, &ntty);
|
||||
#else /* TERMIOS_H */
|
||||
(void)tcgetattr(ttyfd, &otty);
|
||||
ntty = otty;
|
||||
ntty.c_lflag &= ~(ICANON | ISIG | ECHO);
|
||||
ntty.c_iflag &= IXOFF;
|
||||
ntty.c_oflag &= ~(OPOST);
|
||||
ntty.c_cflag &= ~(PARENB | PARODD);
|
||||
ntty.c_cc[VMIN] = 1;
|
||||
ntty.c_cc[VTIME] = 0;
|
||||
(void)tcsetattr(ttyfd, TCSAFLUSH, &ntty);
|
||||
#endif /* TERMIOS_H */
|
||||
}
|
||||
|
||||
void reset_tty()
|
||||
{
|
||||
(void)sleep(1); /* Wait for output to drain */
|
||||
#ifndef TERMIOS_H
|
||||
(void)ioctl(ttyfd, TIOCSETP, &otty);
|
||||
#else /* TERMIOS_H */
|
||||
(void)tcsetattr(ttyfd, TCSAFLUSH, &otty);
|
||||
#endif /* TERMIOS_H */
|
||||
}
|
||||
|
||||
void cleanup(sig) int sig;
|
||||
{
|
||||
reset_tty();
|
||||
exit(sig);
|
||||
}
|
||||
|
||||
void timedout()
|
||||
{
|
||||
(void)signal(SIGALRM, timedout);
|
||||
longjmp(timobuf, 1);
|
||||
}
|
||||
|
||||
int tgetc(timeout)
|
||||
int timeout;
|
||||
{
|
||||
char c;
|
||||
int i;
|
||||
|
||||
if(time_out) {
|
||||
if(setjmp(timobuf)) {
|
||||
return TMO;
|
||||
}
|
||||
(void)alarm(timeout);
|
||||
}
|
||||
i = read(ttyfd, &c, 1);
|
||||
if(time_out) {
|
||||
(void)alarm(0);
|
||||
}
|
||||
if(i == 0) {
|
||||
return EOT;
|
||||
} else {
|
||||
return c & BYTEMASK;
|
||||
}
|
||||
}
|
||||
|
||||
tgetrec(buf, count, timeout)
|
||||
char *buf;
|
||||
int count, timeout;
|
||||
{
|
||||
int i, tot = 0, cc = count;
|
||||
|
||||
if(time_out) {
|
||||
if(setjmp(timobuf)) {
|
||||
return TMO;
|
||||
}
|
||||
(void)alarm(timeout);
|
||||
}
|
||||
while(tot < count) {
|
||||
i = read(ttyfd, buf, cc);
|
||||
if(i < 0) {
|
||||
continue;
|
||||
}
|
||||
tot += i;
|
||||
cc -= i;
|
||||
buf += i;
|
||||
}
|
||||
if(time_out) {
|
||||
(void)alarm(0);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
void tputc(c)
|
||||
int c;
|
||||
{
|
||||
char cc;
|
||||
|
||||
cc = c & BYTEMASK;
|
||||
(void)write(ttyfd, &cc, 1);
|
||||
}
|
||||
|
||||
void tputrec(buf, count)
|
||||
char *buf;
|
||||
int count;
|
||||
{
|
||||
(void)write(ttyfd, buf, count);
|
||||
}
|
||||
|
164
comm/xm_from.c
Executable file
164
comm/xm_from.c
Executable file
@ -0,0 +1,164 @@
|
||||
#include "comm.h"
|
||||
#ifdef XM
|
||||
#include <stdio.h>
|
||||
#include "../fileio/machdr.h"
|
||||
#include "../fileio/wrfile.h"
|
||||
#include "../util/masks.h"
|
||||
#include "globals.h"
|
||||
#include "protocol.h"
|
||||
|
||||
extern int tgetc();
|
||||
extern int tgetrec();
|
||||
extern void tputc();
|
||||
|
||||
static void receive_part();
|
||||
static int receive_sync();
|
||||
static int receive_rec();
|
||||
|
||||
char info[INFOBYTES];
|
||||
|
||||
void xm_from()
|
||||
{
|
||||
unsigned long data_size, rsrc_size;
|
||||
char text[64];
|
||||
|
||||
if(receive_sync() == ACK) {
|
||||
receive_part(info, DATABYTES, 1);
|
||||
transname(info + I_NAMEOFF + 1, text, info[I_NAMEOFF]);
|
||||
define_name(text);
|
||||
data_size = get4(info + I_DLENOFF);
|
||||
rsrc_size = get4(info + I_RLENOFF);
|
||||
start_info(info, rsrc_size, data_size);
|
||||
start_data();
|
||||
receive_part(out_buffer, data_size, 1);
|
||||
start_rsrc();
|
||||
receive_part(out_buffer, rsrc_size, 0);
|
||||
end_file();
|
||||
}
|
||||
}
|
||||
|
||||
static void receive_part(info, size, more)
|
||||
char *info;
|
||||
int size, more;
|
||||
{
|
||||
int recno = 1, i, status, naks = 0;
|
||||
|
||||
status = 0;
|
||||
while(status != EOT) {
|
||||
status = receive_rec(info, DATABYTES, recno);
|
||||
switch(status) {
|
||||
case EOT:
|
||||
if(!pre_beta) {
|
||||
tputc(ACK);
|
||||
}
|
||||
if(more) {
|
||||
tputc(NAK);
|
||||
}
|
||||
size = 0;
|
||||
break;
|
||||
case ACK:
|
||||
tputc(ACK);
|
||||
naks = 0;
|
||||
size -= DATABYTES;
|
||||
info += DATABYTES;
|
||||
recno = (recno + 1) & MAXRECNO;
|
||||
break;
|
||||
case DUP:
|
||||
tputc(ACK);
|
||||
naks = 0;
|
||||
break;
|
||||
case NAK:
|
||||
if(naks++ < RETRIES) {
|
||||
tputc(NAK);
|
||||
break;
|
||||
}
|
||||
case CAN:
|
||||
tputc(CAN);
|
||||
cleanup(-1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static int receive_sync()
|
||||
{
|
||||
int c;
|
||||
|
||||
for(;;) {
|
||||
c = tgetc(60);
|
||||
switch(c) {
|
||||
case ESC:
|
||||
break;
|
||||
case CAN:
|
||||
cleanup();
|
||||
break;
|
||||
case EOT:
|
||||
case TMO:
|
||||
return c;
|
||||
default:
|
||||
continue;
|
||||
}
|
||||
c = tgetc(1);
|
||||
if(c == 'a') {
|
||||
break;;
|
||||
}
|
||||
}
|
||||
tputc(ACK);
|
||||
return ACK;
|
||||
}
|
||||
|
||||
static int receive_rec(buf, bufsize, recno)
|
||||
char *buf;
|
||||
int bufsize, recno;
|
||||
{
|
||||
int i, cksum, c, rec, recbar;
|
||||
char *bp;
|
||||
|
||||
c = tgetc(SOHTIMO);
|
||||
switch(c) {
|
||||
case EOT:
|
||||
case CAN:
|
||||
return c;
|
||||
case SOH:
|
||||
break;
|
||||
case TMO:
|
||||
default:
|
||||
return NAK;
|
||||
}
|
||||
rec = tgetc(CHRTIMO);
|
||||
if(rec == TMO) {
|
||||
return NAK;
|
||||
}
|
||||
recbar = tgetc(CHRTIMO);
|
||||
if(recbar == TMO) {
|
||||
return NAK;
|
||||
}
|
||||
if(rec + recbar != MAXRECNO) {
|
||||
return NAK;
|
||||
}
|
||||
if(tgetrec(buf, bufsize, LINTIMO) == TMO) {
|
||||
return NAK;
|
||||
}
|
||||
bp = buf;
|
||||
cksum = 0;
|
||||
for(i = 0; i < bufsize; i++) {
|
||||
cksum += *bp++ & BYTEMASK;
|
||||
}
|
||||
c = tgetc(CHRTIMO);
|
||||
if(c == TMO) {
|
||||
return NAK;
|
||||
}
|
||||
if(c != (cksum & BYTEMASK)) {
|
||||
return NAK;
|
||||
}
|
||||
if(rec == recno - 1) {
|
||||
return DUP;
|
||||
}
|
||||
if(rec != recno) {
|
||||
return CAN;
|
||||
}
|
||||
return ACK;
|
||||
}
|
||||
|
||||
#else /* XM */
|
||||
int xm_from; /* Keep lint and some compilers happy */
|
||||
#endif /* XM */
|
98
comm/xm_to.c
Executable file
98
comm/xm_to.c
Executable file
@ -0,0 +1,98 @@
|
||||
#include "comm.h"
|
||||
#ifdef XM
|
||||
#include "../fileio/machdr.h"
|
||||
#include "../fileio/rdfile.h"
|
||||
#include "../util/masks.h"
|
||||
#include "globals.h"
|
||||
#include "protocol.h"
|
||||
|
||||
extern int tgetc();
|
||||
extern void tputc();
|
||||
extern void tputrec();
|
||||
|
||||
static void send_part();
|
||||
static int send_sync();
|
||||
static void send_rec();
|
||||
|
||||
void xm_to()
|
||||
{
|
||||
if(send_sync() == ACK) {
|
||||
send_part(file_info, DATABYTES, 1);
|
||||
send_part(data_fork, data_size, 1);
|
||||
send_part(rsrc_fork, rsrc_size, 0);
|
||||
}
|
||||
}
|
||||
|
||||
static void send_part(info, size, more)
|
||||
char *info;
|
||||
int size, more;
|
||||
{
|
||||
int recno = 1, i, status;
|
||||
|
||||
while(size > 0) {
|
||||
for(i = 0; i < RETRIES; i++) {
|
||||
send_rec(info, DATABYTES, recno);
|
||||
status = tgetc(ACKTIMO);
|
||||
if(status != NAK) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
if(status == NAK || status == CAN) {
|
||||
cleanup(-1);
|
||||
}
|
||||
size -= DATABYTES;
|
||||
info += DATABYTES;
|
||||
recno = (recno + 1) & MAXRECNO;
|
||||
}
|
||||
tputc(EOT);
|
||||
if(!pre_beta) {
|
||||
status = tgetc(ACKTIMO);
|
||||
}
|
||||
if(more) {
|
||||
status = tgetc(ACKTIMO);
|
||||
}
|
||||
}
|
||||
|
||||
static int send_sync()
|
||||
{
|
||||
int c, i;
|
||||
|
||||
for(i = 0; i < 3; i++) {
|
||||
tputc(ESC);
|
||||
tputc('a');
|
||||
while((c = tgetc(ACKTIMO)) != TMO) {
|
||||
switch(c) {
|
||||
case CAN:
|
||||
case EOT:
|
||||
case ACK:
|
||||
return c;
|
||||
default:
|
||||
continue;
|
||||
}
|
||||
}
|
||||
}
|
||||
return CAN;
|
||||
}
|
||||
|
||||
static void send_rec(buf, bufsize, recno)
|
||||
char *buf;
|
||||
int bufsize, recno;
|
||||
{
|
||||
int i, cksum;
|
||||
char *bp;
|
||||
|
||||
cksum = 0;
|
||||
bp = buf;
|
||||
for(i = 0; i < bufsize; i++) {
|
||||
cksum += *bp++ & BYTEMASK;
|
||||
}
|
||||
tputc(SOH);
|
||||
tputc((unsigned char)recno);
|
||||
tputc((unsigned char)(MAXRECNO - recno));
|
||||
tputrec(buf, bufsize);
|
||||
tputc((char)(cksum & BYTEMASK));
|
||||
}
|
||||
|
||||
#else /* XM */
|
||||
int xm_to; /* Keep lint and some compilers happy */
|
||||
#endif /* XM */
|
5
comm/ym_from.c
Executable file
5
comm/ym_from.c
Executable file
@ -0,0 +1,5 @@
|
||||
#include "comm.h"
|
||||
#ifdef YM
|
||||
#else /* YM */
|
||||
int ym_from; /* Keep lint and some compilers happy */
|
||||
#endif /* YM */
|
5
comm/ym_to.c
Executable file
5
comm/ym_to.c
Executable file
@ -0,0 +1,5 @@
|
||||
#include "comm.h"
|
||||
#ifdef YM
|
||||
#else /* YM */
|
||||
int ym_to; /* Keep lint and some compilers happy */
|
||||
#endif /* YM */
|
5
comm/zm_from.c
Executable file
5
comm/zm_from.c
Executable file
@ -0,0 +1,5 @@
|
||||
#include "comm.h"
|
||||
#ifdef ZM
|
||||
#else /* ZM */
|
||||
int zm_from; /* Keep lint and some compilers happy */
|
||||
#endif /* ZM */
|
5
comm/zm_to.c
Executable file
5
comm/zm_to.c
Executable file
@ -0,0 +1,5 @@
|
||||
#include "comm.h"
|
||||
#ifdef ZM
|
||||
#else /* ZM */
|
||||
int zm_to; /* Keep lint and some compilers happy */
|
||||
#endif /* ZM */
|
55
crc/arc.c
Normal file
55
crc/arc.c
Normal file
@ -0,0 +1,55 @@
|
||||
unsigned long arc_crcinit = 0;
|
||||
|
||||
static unsigned short crctab[256] = {
|
||||
0x0000, 0xc0c1, 0xc181, 0x0140, 0xc301, 0x03c0, 0x0280, 0xc241,
|
||||
0xc601, 0x06c0, 0x0780, 0xc741, 0x0500, 0xc5c1, 0xc481, 0x0440,
|
||||
0xcc01, 0x0cc0, 0x0d80, 0xcd41, 0x0f00, 0xcfc1, 0xce81, 0x0e40,
|
||||
0x0a00, 0xcac1, 0xcb81, 0x0b40, 0xc901, 0x09c0, 0x0880, 0xc841,
|
||||
0xd801, 0x18c0, 0x1980, 0xd941, 0x1b00, 0xdbc1, 0xda81, 0x1a40,
|
||||
0x1e00, 0xdec1, 0xdf81, 0x1f40, 0xdd01, 0x1dc0, 0x1c80, 0xdc41,
|
||||
0x1400, 0xd4c1, 0xd581, 0x1540, 0xd701, 0x17c0, 0x1680, 0xd641,
|
||||
0xd201, 0x12c0, 0x1380, 0xd341, 0x1100, 0xd1c1, 0xd081, 0x1040,
|
||||
0xf001, 0x30c0, 0x3180, 0xf141, 0x3300, 0xf3c1, 0xf281, 0x3240,
|
||||
0x3600, 0xf6c1, 0xf781, 0x3740, 0xf501, 0x35c0, 0x3480, 0xf441,
|
||||
0x3c00, 0xfcc1, 0xfd81, 0x3d40, 0xff01, 0x3fc0, 0x3e80, 0xfe41,
|
||||
0xfa01, 0x3ac0, 0x3b80, 0xfb41, 0x3900, 0xf9c1, 0xf881, 0x3840,
|
||||
0x2800, 0xe8c1, 0xe981, 0x2940, 0xeb01, 0x2bc0, 0x2a80, 0xea41,
|
||||
0xee01, 0x2ec0, 0x2f80, 0xef41, 0x2d00, 0xedc1, 0xec81, 0x2c40,
|
||||
0xe401, 0x24c0, 0x2580, 0xe541, 0x2700, 0xe7c1, 0xe681, 0x2640,
|
||||
0x2200, 0xe2c1, 0xe381, 0x2340, 0xe101, 0x21c0, 0x2080, 0xe041,
|
||||
0xa001, 0x60c0, 0x6180, 0xa141, 0x6300, 0xa3c1, 0xa281, 0x6240,
|
||||
0x6600, 0xa6c1, 0xa781, 0x6740, 0xa501, 0x65c0, 0x6480, 0xa441,
|
||||
0x6c00, 0xacc1, 0xad81, 0x6d40, 0xaf01, 0x6fc0, 0x6e80, 0xae41,
|
||||
0xaa01, 0x6ac0, 0x6b80, 0xab41, 0x6900, 0xa9c1, 0xa881, 0x6840,
|
||||
0x7800, 0xb8c1, 0xb981, 0x7940, 0xbb01, 0x7bc0, 0x7a80, 0xba41,
|
||||
0xbe01, 0x7ec0, 0x7f80, 0xbf41, 0x7d00, 0xbdc1, 0xbc81, 0x7c40,
|
||||
0xb401, 0x74c0, 0x7580, 0xb541, 0x7700, 0xb7c1, 0xb681, 0x7640,
|
||||
0x7200, 0xb2c1, 0xb381, 0x7340, 0xb101, 0x71c0, 0x7080, 0xb041,
|
||||
0x5000, 0x90c1, 0x9181, 0x5140, 0x9301, 0x53c0, 0x5280, 0x9241,
|
||||
0x9601, 0x56c0, 0x5780, 0x9741, 0x5500, 0x95c1, 0x9481, 0x5440,
|
||||
0x9c01, 0x5cc0, 0x5d80, 0x9d41, 0x5f00, 0x9fc1, 0x9e81, 0x5e40,
|
||||
0x5a00, 0x9ac1, 0x9b81, 0x5b40, 0x9901, 0x59c0, 0x5880, 0x9841,
|
||||
0x8801, 0x48c0, 0x4980, 0x8941, 0x4b00, 0x8bc1, 0x8a81, 0x4a40,
|
||||
0x4e00, 0x8ec1, 0x8f81, 0x4f40, 0x8d01, 0x4dc0, 0x4c80, 0x8c41,
|
||||
0x4400, 0x84c1, 0x8581, 0x4540, 0x8701, 0x47c0, 0x4680, 0x8641,
|
||||
0x8201, 0x42c0, 0x4380, 0x8341, 0x4100, 0x81c1, 0x8081, 0x4040,
|
||||
};
|
||||
|
||||
unsigned long arc_updcrc(icrc, icp, icnt)
|
||||
unsigned long icrc;
|
||||
unsigned char *icp;
|
||||
int icnt;
|
||||
{
|
||||
#define M1 0xff
|
||||
#define M2 0xff00
|
||||
register unsigned long crc = icrc;
|
||||
register unsigned char *cp = icp;
|
||||
register int cnt = icnt;
|
||||
|
||||
while(cnt--) {
|
||||
crc=((crc>>8)&M1)^crctab[(crc&0xff)^*cp++];
|
||||
}
|
||||
|
||||
return(crc);
|
||||
}
|
||||
|
55
crc/binhex.c
Normal file
55
crc/binhex.c
Normal file
@ -0,0 +1,55 @@
|
||||
unsigned long binhex_crcinit = 0;
|
||||
|
||||
static unsigned short crctab[256] = {
|
||||
0x0000, 0x1021, 0x2042, 0x3063, 0x4084, 0x50a5, 0x60c6, 0x70e7,
|
||||
0x8108, 0x9129, 0xa14a, 0xb16b, 0xc18c, 0xd1ad, 0xe1ce, 0xf1ef,
|
||||
0x1231, 0x0210, 0x3273, 0x2252, 0x52b5, 0x4294, 0x72f7, 0x62d6,
|
||||
0x9339, 0x8318, 0xb37b, 0xa35a, 0xd3bd, 0xc39c, 0xf3ff, 0xe3de,
|
||||
0x2462, 0x3443, 0x0420, 0x1401, 0x64e6, 0x74c7, 0x44a4, 0x5485,
|
||||
0xa56a, 0xb54b, 0x8528, 0x9509, 0xe5ee, 0xf5cf, 0xc5ac, 0xd58d,
|
||||
0x3653, 0x2672, 0x1611, 0x0630, 0x76d7, 0x66f6, 0x5695, 0x46b4,
|
||||
0xb75b, 0xa77a, 0x9719, 0x8738, 0xf7df, 0xe7fe, 0xd79d, 0xc7bc,
|
||||
0x48c4, 0x58e5, 0x6886, 0x78a7, 0x0840, 0x1861, 0x2802, 0x3823,
|
||||
0xc9cc, 0xd9ed, 0xe98e, 0xf9af, 0x8948, 0x9969, 0xa90a, 0xb92b,
|
||||
0x5af5, 0x4ad4, 0x7ab7, 0x6a96, 0x1a71, 0x0a50, 0x3a33, 0x2a12,
|
||||
0xdbfd, 0xcbdc, 0xfbbf, 0xeb9e, 0x9b79, 0x8b58, 0xbb3b, 0xab1a,
|
||||
0x6ca6, 0x7c87, 0x4ce4, 0x5cc5, 0x2c22, 0x3c03, 0x0c60, 0x1c41,
|
||||
0xedae, 0xfd8f, 0xcdec, 0xddcd, 0xad2a, 0xbd0b, 0x8d68, 0x9d49,
|
||||
0x7e97, 0x6eb6, 0x5ed5, 0x4ef4, 0x3e13, 0x2e32, 0x1e51, 0x0e70,
|
||||
0xff9f, 0xefbe, 0xdfdd, 0xcffc, 0xbf1b, 0xaf3a, 0x9f59, 0x8f78,
|
||||
0x9188, 0x81a9, 0xb1ca, 0xa1eb, 0xd10c, 0xc12d, 0xf14e, 0xe16f,
|
||||
0x1080, 0x00a1, 0x30c2, 0x20e3, 0x5004, 0x4025, 0x7046, 0x6067,
|
||||
0x83b9, 0x9398, 0xa3fb, 0xb3da, 0xc33d, 0xd31c, 0xe37f, 0xf35e,
|
||||
0x02b1, 0x1290, 0x22f3, 0x32d2, 0x4235, 0x5214, 0x6277, 0x7256,
|
||||
0xb5ea, 0xa5cb, 0x95a8, 0x8589, 0xf56e, 0xe54f, 0xd52c, 0xc50d,
|
||||
0x34e2, 0x24c3, 0x14a0, 0x0481, 0x7466, 0x6447, 0x5424, 0x4405,
|
||||
0xa7db, 0xb7fa, 0x8799, 0x97b8, 0xe75f, 0xf77e, 0xc71d, 0xd73c,
|
||||
0x26d3, 0x36f2, 0x0691, 0x16b0, 0x6657, 0x7676, 0x4615, 0x5634,
|
||||
0xd94c, 0xc96d, 0xf90e, 0xe92f, 0x99c8, 0x89e9, 0xb98a, 0xa9ab,
|
||||
0x5844, 0x4865, 0x7806, 0x6827, 0x18c0, 0x08e1, 0x3882, 0x28a3,
|
||||
0xcb7d, 0xdb5c, 0xeb3f, 0xfb1e, 0x8bf9, 0x9bd8, 0xabbb, 0xbb9a,
|
||||
0x4a75, 0x5a54, 0x6a37, 0x7a16, 0x0af1, 0x1ad0, 0x2ab3, 0x3a92,
|
||||
0xfd2e, 0xed0f, 0xdd6c, 0xcd4d, 0xbdaa, 0xad8b, 0x9de8, 0x8dc9,
|
||||
0x7c26, 0x6c07, 0x5c64, 0x4c45, 0x3ca2, 0x2c83, 0x1ce0, 0x0cc1,
|
||||
0xef1f, 0xff3e, 0xcf5d, 0xdf7c, 0xaf9b, 0xbfba, 0x8fd9, 0x9ff8,
|
||||
0x6e17, 0x7e36, 0x4e55, 0x5e74, 0x2e93, 0x3eb2, 0x0ed1, 0x1ef0,
|
||||
};
|
||||
|
||||
unsigned long binhex_updcrc(icrc, icp, icnt)
|
||||
unsigned long icrc;
|
||||
unsigned char *icp;
|
||||
int icnt;
|
||||
{
|
||||
#define M1 0xff
|
||||
#define M2 0xff00
|
||||
register unsigned long crc = icrc;
|
||||
register unsigned char *cp = icp;
|
||||
register int cnt = icnt;
|
||||
|
||||
while(cnt--) {
|
||||
crc=((crc<<8)&M2)^crctab[((crc>>8)&0xff)^*cp++];
|
||||
}
|
||||
|
||||
return(crc);
|
||||
}
|
||||
|
BIN
crc/binhex.o
Normal file
BIN
crc/binhex.o
Normal file
Binary file not shown.
55
crc/ccitt.c
Normal file
55
crc/ccitt.c
Normal file
@ -0,0 +1,55 @@
|
||||
unsigned long ccitt_crcinit = 65535;
|
||||
|
||||
static unsigned short crctab[256] = {
|
||||
0x0000, 0x1021, 0x2042, 0x3063, 0x4084, 0x50a5, 0x60c6, 0x70e7,
|
||||
0x8108, 0x9129, 0xa14a, 0xb16b, 0xc18c, 0xd1ad, 0xe1ce, 0xf1ef,
|
||||
0x1231, 0x0210, 0x3273, 0x2252, 0x52b5, 0x4294, 0x72f7, 0x62d6,
|
||||
0x9339, 0x8318, 0xb37b, 0xa35a, 0xd3bd, 0xc39c, 0xf3ff, 0xe3de,
|
||||
0x2462, 0x3443, 0x0420, 0x1401, 0x64e6, 0x74c7, 0x44a4, 0x5485,
|
||||
0xa56a, 0xb54b, 0x8528, 0x9509, 0xe5ee, 0xf5cf, 0xc5ac, 0xd58d,
|
||||
0x3653, 0x2672, 0x1611, 0x0630, 0x76d7, 0x66f6, 0x5695, 0x46b4,
|
||||
0xb75b, 0xa77a, 0x9719, 0x8738, 0xf7df, 0xe7fe, 0xd79d, 0xc7bc,
|
||||
0x48c4, 0x58e5, 0x6886, 0x78a7, 0x0840, 0x1861, 0x2802, 0x3823,
|
||||
0xc9cc, 0xd9ed, 0xe98e, 0xf9af, 0x8948, 0x9969, 0xa90a, 0xb92b,
|
||||
0x5af5, 0x4ad4, 0x7ab7, 0x6a96, 0x1a71, 0x0a50, 0x3a33, 0x2a12,
|
||||
0xdbfd, 0xcbdc, 0xfbbf, 0xeb9e, 0x9b79, 0x8b58, 0xbb3b, 0xab1a,
|
||||
0x6ca6, 0x7c87, 0x4ce4, 0x5cc5, 0x2c22, 0x3c03, 0x0c60, 0x1c41,
|
||||
0xedae, 0xfd8f, 0xcdec, 0xddcd, 0xad2a, 0xbd0b, 0x8d68, 0x9d49,
|
||||
0x7e97, 0x6eb6, 0x5ed5, 0x4ef4, 0x3e13, 0x2e32, 0x1e51, 0x0e70,
|
||||
0xff9f, 0xefbe, 0xdfdd, 0xcffc, 0xbf1b, 0xaf3a, 0x9f59, 0x8f78,
|
||||
0x9188, 0x81a9, 0xb1ca, 0xa1eb, 0xd10c, 0xc12d, 0xf14e, 0xe16f,
|
||||
0x1080, 0x00a1, 0x30c2, 0x20e3, 0x5004, 0x4025, 0x7046, 0x6067,
|
||||
0x83b9, 0x9398, 0xa3fb, 0xb3da, 0xc33d, 0xd31c, 0xe37f, 0xf35e,
|
||||
0x02b1, 0x1290, 0x22f3, 0x32d2, 0x4235, 0x5214, 0x6277, 0x7256,
|
||||
0xb5ea, 0xa5cb, 0x95a8, 0x8589, 0xf56e, 0xe54f, 0xd52c, 0xc50d,
|
||||
0x34e2, 0x24c3, 0x14a0, 0x0481, 0x7466, 0x6447, 0x5424, 0x4405,
|
||||
0xa7db, 0xb7fa, 0x8799, 0x97b8, 0xe75f, 0xf77e, 0xc71d, 0xd73c,
|
||||
0x26d3, 0x36f2, 0x0691, 0x16b0, 0x6657, 0x7676, 0x4615, 0x5634,
|
||||
0xd94c, 0xc96d, 0xf90e, 0xe92f, 0x99c8, 0x89e9, 0xb98a, 0xa9ab,
|
||||
0x5844, 0x4865, 0x7806, 0x6827, 0x18c0, 0x08e1, 0x3882, 0x28a3,
|
||||
0xcb7d, 0xdb5c, 0xeb3f, 0xfb1e, 0x8bf9, 0x9bd8, 0xabbb, 0xbb9a,
|
||||
0x4a75, 0x5a54, 0x6a37, 0x7a16, 0x0af1, 0x1ad0, 0x2ab3, 0x3a92,
|
||||
0xfd2e, 0xed0f, 0xdd6c, 0xcd4d, 0xbdaa, 0xad8b, 0x9de8, 0x8dc9,
|
||||
0x7c26, 0x6c07, 0x5c64, 0x4c45, 0x3ca2, 0x2c83, 0x1ce0, 0x0cc1,
|
||||
0xef1f, 0xff3e, 0xcf5d, 0xdf7c, 0xaf9b, 0xbfba, 0x8fd9, 0x9ff8,
|
||||
0x6e17, 0x7e36, 0x4e55, 0x5e74, 0x2e93, 0x3eb2, 0x0ed1, 0x1ef0,
|
||||
};
|
||||
|
||||
unsigned long ccitt_updcrc(icrc, icp, icnt)
|
||||
unsigned long icrc;
|
||||
unsigned char *icp;
|
||||
int icnt;
|
||||
{
|
||||
#define M1 0xff
|
||||
#define M2 0xff00
|
||||
register unsigned long crc = icrc;
|
||||
register unsigned char *cp = icp;
|
||||
register int cnt = icnt;
|
||||
|
||||
while(cnt--) {
|
||||
crc=((crc<<8)&M2)^crctab[((crc>>8)&0xff)^*cp++];
|
||||
}
|
||||
|
||||
return(crc);
|
||||
}
|
||||
|
BIN
crc/ccitt.o
Normal file
BIN
crc/ccitt.o
Normal file
Binary file not shown.
87
crc/ccitt32.c
Normal file
87
crc/ccitt32.c
Normal file
@ -0,0 +1,87 @@
|
||||
unsigned long ccitt32_crcinit = -1;
|
||||
|
||||
static unsigned long crctab[256] = {
|
||||
0x00000000, 0x04c11db7, 0x09823b6e, 0x0d4326d9,
|
||||
0x130476dc, 0x17c56b6b, 0x1a864db2, 0x1e475005,
|
||||
0x2608edb8, 0x22c9f00f, 0x2f8ad6d6, 0x2b4bcb61,
|
||||
0x350c9b64, 0x31cd86d3, 0x3c8ea00a, 0x384fbdbd,
|
||||
0x4c11db70, 0x48d0c6c7, 0x4593e01e, 0x4152fda9,
|
||||
0x5f15adac, 0x5bd4b01b, 0x569796c2, 0x52568b75,
|
||||
0x6a1936c8, 0x6ed82b7f, 0x639b0da6, 0x675a1011,
|
||||
0x791d4014, 0x7ddc5da3, 0x709f7b7a, 0x745e66cd,
|
||||
0x9823b6e0, 0x9ce2ab57, 0x91a18d8e, 0x95609039,
|
||||
0x8b27c03c, 0x8fe6dd8b, 0x82a5fb52, 0x8664e6e5,
|
||||
0xbe2b5b58, 0xbaea46ef, 0xb7a96036, 0xb3687d81,
|
||||
0xad2f2d84, 0xa9ee3033, 0xa4ad16ea, 0xa06c0b5d,
|
||||
0xd4326d90, 0xd0f37027, 0xddb056fe, 0xd9714b49,
|
||||
0xc7361b4c, 0xc3f706fb, 0xceb42022, 0xca753d95,
|
||||
0xf23a8028, 0xf6fb9d9f, 0xfbb8bb46, 0xff79a6f1,
|
||||
0xe13ef6f4, 0xe5ffeb43, 0xe8bccd9a, 0xec7dd02d,
|
||||
0x34867077, 0x30476dc0, 0x3d044b19, 0x39c556ae,
|
||||
0x278206ab, 0x23431b1c, 0x2e003dc5, 0x2ac12072,
|
||||
0x128e9dcf, 0x164f8078, 0x1b0ca6a1, 0x1fcdbb16,
|
||||
0x018aeb13, 0x054bf6a4, 0x0808d07d, 0x0cc9cdca,
|
||||
0x7897ab07, 0x7c56b6b0, 0x71159069, 0x75d48dde,
|
||||
0x6b93dddb, 0x6f52c06c, 0x6211e6b5, 0x66d0fb02,
|
||||
0x5e9f46bf, 0x5a5e5b08, 0x571d7dd1, 0x53dc6066,
|
||||
0x4d9b3063, 0x495a2dd4, 0x44190b0d, 0x40d816ba,
|
||||
0xaca5c697, 0xa864db20, 0xa527fdf9, 0xa1e6e04e,
|
||||
0xbfa1b04b, 0xbb60adfc, 0xb6238b25, 0xb2e29692,
|
||||
0x8aad2b2f, 0x8e6c3698, 0x832f1041, 0x87ee0df6,
|
||||
0x99a95df3, 0x9d684044, 0x902b669d, 0x94ea7b2a,
|
||||
0xe0b41de7, 0xe4750050, 0xe9362689, 0xedf73b3e,
|
||||
0xf3b06b3b, 0xf771768c, 0xfa325055, 0xfef34de2,
|
||||
0xc6bcf05f, 0xc27dede8, 0xcf3ecb31, 0xcbffd686,
|
||||
0xd5b88683, 0xd1799b34, 0xdc3abded, 0xd8fba05a,
|
||||
0x690ce0ee, 0x6dcdfd59, 0x608edb80, 0x644fc637,
|
||||
0x7a089632, 0x7ec98b85, 0x738aad5c, 0x774bb0eb,
|
||||
0x4f040d56, 0x4bc510e1, 0x46863638, 0x42472b8f,
|
||||
0x5c007b8a, 0x58c1663d, 0x558240e4, 0x51435d53,
|
||||
0x251d3b9e, 0x21dc2629, 0x2c9f00f0, 0x285e1d47,
|
||||
0x36194d42, 0x32d850f5, 0x3f9b762c, 0x3b5a6b9b,
|
||||
0x0315d626, 0x07d4cb91, 0x0a97ed48, 0x0e56f0ff,
|
||||
0x1011a0fa, 0x14d0bd4d, 0x19939b94, 0x1d528623,
|
||||
0xf12f560e, 0xf5ee4bb9, 0xf8ad6d60, 0xfc6c70d7,
|
||||
0xe22b20d2, 0xe6ea3d65, 0xeba91bbc, 0xef68060b,
|
||||
0xd727bbb6, 0xd3e6a601, 0xdea580d8, 0xda649d6f,
|
||||
0xc423cd6a, 0xc0e2d0dd, 0xcda1f604, 0xc960ebb3,
|
||||
0xbd3e8d7e, 0xb9ff90c9, 0xb4bcb610, 0xb07daba7,
|
||||
0xae3afba2, 0xaafbe615, 0xa7b8c0cc, 0xa379dd7b,
|
||||
0x9b3660c6, 0x9ff77d71, 0x92b45ba8, 0x9675461f,
|
||||
0x8832161a, 0x8cf30bad, 0x81b02d74, 0x857130c3,
|
||||
0x5d8a9099, 0x594b8d2e, 0x5408abf7, 0x50c9b640,
|
||||
0x4e8ee645, 0x4a4ffbf2, 0x470cdd2b, 0x43cdc09c,
|
||||
0x7b827d21, 0x7f436096, 0x7200464f, 0x76c15bf8,
|
||||
0x68860bfd, 0x6c47164a, 0x61043093, 0x65c52d24,
|
||||
0x119b4be9, 0x155a565e, 0x18197087, 0x1cd86d30,
|
||||
0x029f3d35, 0x065e2082, 0x0b1d065b, 0x0fdc1bec,
|
||||
0x3793a651, 0x3352bbe6, 0x3e119d3f, 0x3ad08088,
|
||||
0x2497d08d, 0x2056cd3a, 0x2d15ebe3, 0x29d4f654,
|
||||
0xc5a92679, 0xc1683bce, 0xcc2b1d17, 0xc8ea00a0,
|
||||
0xd6ad50a5, 0xd26c4d12, 0xdf2f6bcb, 0xdbee767c,
|
||||
0xe3a1cbc1, 0xe760d676, 0xea23f0af, 0xeee2ed18,
|
||||
0xf0a5bd1d, 0xf464a0aa, 0xf9278673, 0xfde69bc4,
|
||||
0x89b8fd09, 0x8d79e0be, 0x803ac667, 0x84fbdbd0,
|
||||
0x9abc8bd5, 0x9e7d9662, 0x933eb0bb, 0x97ffad0c,
|
||||
0xafb010b1, 0xab710d06, 0xa6322bdf, 0xa2f33668,
|
||||
0xbcb4666d, 0xb8757bda, 0xb5365d03, 0xb1f740b4,
|
||||
};
|
||||
|
||||
unsigned long ccitt32_updcrc(icrc, icp, icnt)
|
||||
unsigned long icrc;
|
||||
unsigned char *icp;
|
||||
int icnt;
|
||||
{
|
||||
#define M1 0xffffff
|
||||
#define M2 0xffffff00
|
||||
register unsigned long crc = icrc;
|
||||
register unsigned char *cp = icp;
|
||||
register int cnt = icnt;
|
||||
|
||||
while(cnt--) {
|
||||
crc=((crc<<8)&M2)^crctab[((crc>>24)&0xff)^*cp++];
|
||||
}
|
||||
|
||||
return(crc);
|
||||
}
|
||||
|
BIN
crc/ccitt32.o
Normal file
BIN
crc/ccitt32.o
Normal file
Binary file not shown.
55
crc/kermit.c
Normal file
55
crc/kermit.c
Normal file
@ -0,0 +1,55 @@
|
||||
unsigned long kermit_crcinit = 0;
|
||||
|
||||
static unsigned short crctab[256] = {
|
||||
0x0000, 0x1189, 0x2312, 0x329b, 0x4624, 0x57ad, 0x6536, 0x74bf,
|
||||
0x8c48, 0x9dc1, 0xaf5a, 0xbed3, 0xca6c, 0xdbe5, 0xe97e, 0xf8f7,
|
||||
0x1081, 0x0108, 0x3393, 0x221a, 0x56a5, 0x472c, 0x75b7, 0x643e,
|
||||
0x9cc9, 0x8d40, 0xbfdb, 0xae52, 0xdaed, 0xcb64, 0xf9ff, 0xe876,
|
||||
0x2102, 0x308b, 0x0210, 0x1399, 0x6726, 0x76af, 0x4434, 0x55bd,
|
||||
0xad4a, 0xbcc3, 0x8e58, 0x9fd1, 0xeb6e, 0xfae7, 0xc87c, 0xd9f5,
|
||||
0x3183, 0x200a, 0x1291, 0x0318, 0x77a7, 0x662e, 0x54b5, 0x453c,
|
||||
0xbdcb, 0xac42, 0x9ed9, 0x8f50, 0xfbef, 0xea66, 0xd8fd, 0xc974,
|
||||
0x4204, 0x538d, 0x6116, 0x709f, 0x0420, 0x15a9, 0x2732, 0x36bb,
|
||||
0xce4c, 0xdfc5, 0xed5e, 0xfcd7, 0x8868, 0x99e1, 0xab7a, 0xbaf3,
|
||||
0x5285, 0x430c, 0x7197, 0x601e, 0x14a1, 0x0528, 0x37b3, 0x263a,
|
||||
0xdecd, 0xcf44, 0xfddf, 0xec56, 0x98e9, 0x8960, 0xbbfb, 0xaa72,
|
||||
0x6306, 0x728f, 0x4014, 0x519d, 0x2522, 0x34ab, 0x0630, 0x17b9,
|
||||
0xef4e, 0xfec7, 0xcc5c, 0xddd5, 0xa96a, 0xb8e3, 0x8a78, 0x9bf1,
|
||||
0x7387, 0x620e, 0x5095, 0x411c, 0x35a3, 0x242a, 0x16b1, 0x0738,
|
||||
0xffcf, 0xee46, 0xdcdd, 0xcd54, 0xb9eb, 0xa862, 0x9af9, 0x8b70,
|
||||
0x8408, 0x9581, 0xa71a, 0xb693, 0xc22c, 0xd3a5, 0xe13e, 0xf0b7,
|
||||
0x0840, 0x19c9, 0x2b52, 0x3adb, 0x4e64, 0x5fed, 0x6d76, 0x7cff,
|
||||
0x9489, 0x8500, 0xb79b, 0xa612, 0xd2ad, 0xc324, 0xf1bf, 0xe036,
|
||||
0x18c1, 0x0948, 0x3bd3, 0x2a5a, 0x5ee5, 0x4f6c, 0x7df7, 0x6c7e,
|
||||
0xa50a, 0xb483, 0x8618, 0x9791, 0xe32e, 0xf2a7, 0xc03c, 0xd1b5,
|
||||
0x2942, 0x38cb, 0x0a50, 0x1bd9, 0x6f66, 0x7eef, 0x4c74, 0x5dfd,
|
||||
0xb58b, 0xa402, 0x9699, 0x8710, 0xf3af, 0xe226, 0xd0bd, 0xc134,
|
||||
0x39c3, 0x284a, 0x1ad1, 0x0b58, 0x7fe7, 0x6e6e, 0x5cf5, 0x4d7c,
|
||||
0xc60c, 0xd785, 0xe51e, 0xf497, 0x8028, 0x91a1, 0xa33a, 0xb2b3,
|
||||
0x4a44, 0x5bcd, 0x6956, 0x78df, 0x0c60, 0x1de9, 0x2f72, 0x3efb,
|
||||
0xd68d, 0xc704, 0xf59f, 0xe416, 0x90a9, 0x8120, 0xb3bb, 0xa232,
|
||||
0x5ac5, 0x4b4c, 0x79d7, 0x685e, 0x1ce1, 0x0d68, 0x3ff3, 0x2e7a,
|
||||
0xe70e, 0xf687, 0xc41c, 0xd595, 0xa12a, 0xb0a3, 0x8238, 0x93b1,
|
||||
0x6b46, 0x7acf, 0x4854, 0x59dd, 0x2d62, 0x3ceb, 0x0e70, 0x1ff9,
|
||||
0xf78f, 0xe606, 0xd49d, 0xc514, 0xb1ab, 0xa022, 0x92b9, 0x8330,
|
||||
0x7bc7, 0x6a4e, 0x58d5, 0x495c, 0x3de3, 0x2c6a, 0x1ef1, 0x0f78,
|
||||
};
|
||||
|
||||
unsigned long kermit_updcrc(icrc, icp, icnt)
|
||||
unsigned long icrc;
|
||||
unsigned char *icp;
|
||||
int icnt;
|
||||
{
|
||||
#define M1 0xff
|
||||
#define M2 0xff00
|
||||
register unsigned long crc = icrc;
|
||||
register unsigned char *cp = icp;
|
||||
register int cnt = icnt;
|
||||
|
||||
while(cnt--) {
|
||||
crc=((crc>>8)&M1)^crctab[(crc&0xff)^*cp++];
|
||||
}
|
||||
|
||||
return(crc);
|
||||
}
|
||||
|
BIN
crc/kermit.o
Normal file
BIN
crc/kermit.o
Normal file
Binary file not shown.
BIN
crc/libcrc.a
Normal file
BIN
crc/libcrc.a
Normal file
Binary file not shown.
BIN
crc/makecrc
Executable file
BIN
crc/makecrc
Executable file
Binary file not shown.
155
crc/makecrc.c
Executable file
155
crc/makecrc.c
Executable file
@ -0,0 +1,155 @@
|
||||
/* This program will write six C routines for the calculation of
|
||||
* the following CRC's. */
|
||||
|
||||
/* The CRC polynomial.
|
||||
* These 4 values define the crc-polynomial.
|
||||
* If you change them, you must change crctab[]'s initial value to what is
|
||||
* printed by initcrctab() [see 'compile with -DMAKETAB' above].
|
||||
*/
|
||||
|
||||
/* This tables assumes CCITT is MSB first. Swapped means LSB first. In that
|
||||
* case the polynomial is also swapped
|
||||
*/
|
||||
|
||||
/* 16 bit crc's */
|
||||
/* Value used by: CCITT KERMIT ARC BINHEX */
|
||||
/* the poly: 0x1021 0x8408 0xA001 0x1021 */
|
||||
/* original: 0x1021 0x1021 0x8005 0x1021 */
|
||||
/* init value: -1 0 0 0 */
|
||||
/* swapped: no yes yes no */
|
||||
/* bits in CRC: 16 16 16 16 */
|
||||
/* ARC used by LHARC, ZOO, STUFFIT */
|
||||
/* BINHEX used by XMODEM, PACKIT */
|
||||
|
||||
/* 32 bit crc's */
|
||||
/* Value used by: CCITT32 ZIP */
|
||||
/* the poly: 0x04c11db7 0xedb88320 */
|
||||
/* original: 0x04c11db7 0x04c11db7 */
|
||||
/* init value: -1 -1 */
|
||||
/* swapped no yes */
|
||||
/* bits in CRC: 32 32 */
|
||||
/* ZIP used by COMPACTOR */
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
extern void exit();
|
||||
extern char *strcat();
|
||||
|
||||
static void initcrctab();
|
||||
|
||||
main()
|
||||
{
|
||||
initcrctab("ccitt", 0x1021, 0xffff, 0, 16);
|
||||
initcrctab("kermit", 0x8408, 0, 1, 16);
|
||||
initcrctab("arc", 0xa001, 0, 1, 16);
|
||||
initcrctab("binhex", 0x1021, 0, 0, 16);
|
||||
initcrctab("ccitt32",0x04c11db7,0xffffffff,0,32);
|
||||
initcrctab("zip",0xedb88320,0xffffffff,1,32);
|
||||
exit(0);
|
||||
/*NOTREACHED*/
|
||||
}
|
||||
|
||||
static void initcrctab(name, poly, init, swapped, bits)
|
||||
char *name;
|
||||
int poly, init, swapped, bits;
|
||||
{
|
||||
register int b, i;
|
||||
unsigned short v;
|
||||
unsigned long vv;
|
||||
FILE *fd;
|
||||
char buf[20];
|
||||
|
||||
buf[0] = 0;
|
||||
(void)strcat(buf, name);
|
||||
(void)strcat(buf, ".c");
|
||||
if((fd = fopen(buf, "w")) == NULL) {
|
||||
(void)fprintf(stderr, "Cannot open %s for writing\n", buf);
|
||||
exit(1);
|
||||
}
|
||||
(void)fprintf(fd, "unsigned long %s_crcinit = %d;\n", name, init);
|
||||
(void)fprintf(fd, "\n");
|
||||
if(bits == 16) {
|
||||
(void)fprintf(fd, "static unsigned short crctab[256] = {\n");
|
||||
} else {
|
||||
(void)fprintf(fd, "static unsigned long crctab[256] = {\n");
|
||||
}
|
||||
(void)fprintf(fd, " ");
|
||||
if(bits == 16) {
|
||||
for(b = 0; b < 256; ++b) {
|
||||
if(swapped) {
|
||||
for(v = b, i = 8; --i >= 0;)
|
||||
v = v & 1 ? (v>>1)^poly : v>>1;
|
||||
} else {
|
||||
for(v = b<<8, i = 8; --i >= 0;)
|
||||
v = v & 0x8000 ? (v<<1)^poly : v<<1;
|
||||
}
|
||||
(void)fprintf(fd, "0x%.4x,", v & 0xffff);
|
||||
if((b&7) == 7) {
|
||||
(void)fprintf(fd, "\n");
|
||||
if(b != 255) (void)fprintf(fd, " ");
|
||||
} else {
|
||||
(void)fprintf(fd, " ");
|
||||
}
|
||||
}
|
||||
} else {
|
||||
for(b = 0; b < 256; ++b) {
|
||||
if(swapped) {
|
||||
for(vv = b, i = 8; --i >= 0;)
|
||||
vv = vv & 1 ? (vv>>1)^poly : vv>>1;
|
||||
} else {
|
||||
for(vv = b<<24, i = 8; --i >= 0;)
|
||||
vv = vv & 0x80000000 ? (vv<<1)^poly : vv<<1;
|
||||
}
|
||||
(void)fprintf(fd, "0x%.8x,", vv & 0xffffffff);
|
||||
if((b&3) == 3) {
|
||||
(void)fprintf(fd, "\n");
|
||||
if(b != 255) (void)fprintf(fd, " ");
|
||||
} else {
|
||||
(void)fprintf(fd, " ");
|
||||
}
|
||||
}
|
||||
}
|
||||
(void)fprintf(fd, "};\n");
|
||||
(void)fprintf(fd, "\n");
|
||||
(void)fprintf(fd, "unsigned long %s_updcrc(icrc, icp, icnt)\n", name);
|
||||
(void)fprintf(fd, " unsigned long icrc;\n");
|
||||
(void)fprintf(fd, " unsigned char *icp;\n");
|
||||
(void)fprintf(fd, " int icnt;\n");
|
||||
(void)fprintf(fd, "{\n");
|
||||
if(bits == 16) {
|
||||
(void)fprintf(fd, "#define M1 0xff\n");
|
||||
(void)fprintf(fd, "#define M2 0xff00\n");
|
||||
} else {
|
||||
(void)fprintf(fd, "#define M1 0xffffff\n");
|
||||
(void)fprintf(fd, "#define M2 0xffffff00\n");
|
||||
}
|
||||
(void)fprintf(fd, " register unsigned long crc = icrc;\n");
|
||||
(void)fprintf(fd, " register unsigned char *cp = icp;\n");
|
||||
(void)fprintf(fd, " register int cnt = icnt;\n");
|
||||
(void)fprintf(fd, "\n");
|
||||
(void)fprintf(fd, " while(cnt--) {\n");
|
||||
if(bits == 16) {
|
||||
if (swapped) {
|
||||
(void)fprintf(fd,
|
||||
"\tcrc=((crc>>8)&M1)^crctab[(crc&0xff)^*cp++];\n");
|
||||
} else {
|
||||
(void)fprintf(fd,
|
||||
"\tcrc=((crc<<8)&M2)^crctab[((crc>>8)&0xff)^*cp++];\n");
|
||||
}
|
||||
} else {
|
||||
if(swapped) {
|
||||
(void)fprintf(fd,
|
||||
"\tcrc=((crc>>8)&M1)^crctab[(crc&0xff)^*cp++];\n");
|
||||
} else {
|
||||
(void)fprintf(fd,
|
||||
"\tcrc=((crc<<8)&M2)^crctab[((crc>>24)&0xff)^*cp++];\n");
|
||||
}
|
||||
}
|
||||
(void)fprintf(fd, " }\n");
|
||||
(void)fprintf(fd, "\n");
|
||||
(void)fprintf(fd, " return(crc);\n");
|
||||
(void)fprintf(fd, "}\n");
|
||||
(void)fprintf(fd, "\n");
|
||||
(void)fclose(fd);
|
||||
}
|
||||
|
BIN
crc/makecrc.o
Normal file
BIN
crc/makecrc.o
Normal file
Binary file not shown.
27
crc/makefile
Executable file
27
crc/makefile
Executable file
@ -0,0 +1,27 @@
|
||||
CFLAGS = -O $(CF)
|
||||
CRCC = arc.c ccitt.c kermit.c binhex.c ccitt32.c zip.c
|
||||
CRCO = arc.o ccitt.o kermit.o binhex.o ccitt32.o zip.o
|
||||
|
||||
libcrc.a: $(CRCO)
|
||||
ar r libcrc.a $(CRCO)
|
||||
if test -f /usr/bin/ranlib ;\
|
||||
then \
|
||||
ranlib libcrc.a ;\
|
||||
fi
|
||||
|
||||
clean:
|
||||
-rm -f $(CRCC) $(CRCO) libcrc.a makecrc makecrc.o
|
||||
|
||||
$(CRCC): makecrc
|
||||
./makecrc
|
||||
|
||||
makecrc: makecrc.o
|
||||
cc -O -o makecrc makecrc.o
|
||||
|
||||
arc.o: arc.c
|
||||
ccitt.o: ccitt.c
|
||||
kermit.o: kermit.c
|
||||
binhex.o: binhex.c
|
||||
ccitt32.o: ccitt32.c
|
||||
zip.o: zip.c
|
||||
|
87
crc/zip.c
Normal file
87
crc/zip.c
Normal file
@ -0,0 +1,87 @@
|
||||
unsigned long zip_crcinit = -1;
|
||||
|
||||
static unsigned long crctab[256] = {
|
||||
0x00000000, 0x09073096, 0x120e612c, 0x1b0951ba,
|
||||
0xff6dc419, 0xf66af48f, 0xed63a535, 0xe46495a3,
|
||||
0xfedb8832, 0xf7dcb8a4, 0xecd5e91e, 0xe5d2d988,
|
||||
0x01b64c2b, 0x08b17cbd, 0x13b82d07, 0x1abf1d91,
|
||||
0xfdb71064, 0xf4b020f2, 0xefb97148, 0xe6be41de,
|
||||
0x02dad47d, 0x0bdde4eb, 0x10d4b551, 0x19d385c7,
|
||||
0x036c9856, 0x0a6ba8c0, 0x1162f97a, 0x1865c9ec,
|
||||
0xfc015c4f, 0xf5066cd9, 0xee0f3d63, 0xe7080df5,
|
||||
0xfb6e20c8, 0xf269105e, 0xe96041e4, 0xe0677172,
|
||||
0x0403e4d1, 0x0d04d447, 0x160d85fd, 0x1f0ab56b,
|
||||
0x05b5a8fa, 0x0cb2986c, 0x17bbc9d6, 0x1ebcf940,
|
||||
0xfad86ce3, 0xf3df5c75, 0xe8d60dcf, 0xe1d13d59,
|
||||
0x06d930ac, 0x0fde003a, 0x14d75180, 0x1dd06116,
|
||||
0xf9b4f4b5, 0xf0b3c423, 0xebba9599, 0xe2bda50f,
|
||||
0xf802b89e, 0xf1058808, 0xea0cd9b2, 0xe30be924,
|
||||
0x076f7c87, 0x0e684c11, 0x15611dab, 0x1c662d3d,
|
||||
0xf6dc4190, 0xffdb7106, 0xe4d220bc, 0xedd5102a,
|
||||
0x09b18589, 0x00b6b51f, 0x1bbfe4a5, 0x12b8d433,
|
||||
0x0807c9a2, 0x0100f934, 0x1a09a88e, 0x130e9818,
|
||||
0xf76a0dbb, 0xfe6d3d2d, 0xe5646c97, 0xec635c01,
|
||||
0x0b6b51f4, 0x026c6162, 0x196530d8, 0x1062004e,
|
||||
0xf40695ed, 0xfd01a57b, 0xe608f4c1, 0xef0fc457,
|
||||
0xf5b0d9c6, 0xfcb7e950, 0xe7beb8ea, 0xeeb9887c,
|
||||
0x0add1ddf, 0x03da2d49, 0x18d37cf3, 0x11d44c65,
|
||||
0x0db26158, 0x04b551ce, 0x1fbc0074, 0x16bb30e2,
|
||||
0xf2dfa541, 0xfbd895d7, 0xe0d1c46d, 0xe9d6f4fb,
|
||||
0xf369e96a, 0xfa6ed9fc, 0xe1678846, 0xe860b8d0,
|
||||
0x0c042d73, 0x05031de5, 0x1e0a4c5f, 0x170d7cc9,
|
||||
0xf005713c, 0xf90241aa, 0xe20b1010, 0xeb0c2086,
|
||||
0x0f68b525, 0x066f85b3, 0x1d66d409, 0x1461e49f,
|
||||
0x0edef90e, 0x07d9c998, 0x1cd09822, 0x15d7a8b4,
|
||||
0xf1b33d17, 0xf8b40d81, 0xe3bd5c3b, 0xeaba6cad,
|
||||
0xedb88320, 0xe4bfb3b6, 0xffb6e20c, 0xf6b1d29a,
|
||||
0x12d54739, 0x1bd277af, 0x00db2615, 0x09dc1683,
|
||||
0x13630b12, 0x1a643b84, 0x016d6a3e, 0x086a5aa8,
|
||||
0xec0ecf0b, 0xe509ff9d, 0xfe00ae27, 0xf7079eb1,
|
||||
0x100f9344, 0x1908a3d2, 0x0201f268, 0x0b06c2fe,
|
||||
0xef62575d, 0xe66567cb, 0xfd6c3671, 0xf46b06e7,
|
||||
0xeed41b76, 0xe7d32be0, 0xfcda7a5a, 0xf5dd4acc,
|
||||
0x11b9df6f, 0x18beeff9, 0x03b7be43, 0x0ab08ed5,
|
||||
0x16d6a3e8, 0x1fd1937e, 0x04d8c2c4, 0x0ddff252,
|
||||
0xe9bb67f1, 0xe0bc5767, 0xfbb506dd, 0xf2b2364b,
|
||||
0xe80d2bda, 0xe10a1b4c, 0xfa034af6, 0xf3047a60,
|
||||
0x1760efc3, 0x1e67df55, 0x056e8eef, 0x0c69be79,
|
||||
0xeb61b38c, 0xe266831a, 0xf96fd2a0, 0xf068e236,
|
||||
0x140c7795, 0x1d0b4703, 0x060216b9, 0x0f05262f,
|
||||
0x15ba3bbe, 0x1cbd0b28, 0x07b45a92, 0x0eb36a04,
|
||||
0xead7ffa7, 0xe3d0cf31, 0xf8d99e8b, 0xf1deae1d,
|
||||
0x1b64c2b0, 0x1263f226, 0x096aa39c, 0x006d930a,
|
||||
0xe40906a9, 0xed0e363f, 0xf6076785, 0xff005713,
|
||||
0xe5bf4a82, 0xecb87a14, 0xf7b12bae, 0xfeb61b38,
|
||||
0x1ad28e9b, 0x13d5be0d, 0x08dcefb7, 0x01dbdf21,
|
||||
0xe6d3d2d4, 0xefd4e242, 0xf4ddb3f8, 0xfdda836e,
|
||||
0x19be16cd, 0x10b9265b, 0x0bb077e1, 0x02b74777,
|
||||
0x18085ae6, 0x110f6a70, 0x0a063bca, 0x03010b5c,
|
||||
0xe7659eff, 0xee62ae69, 0xf56bffd3, 0xfc6ccf45,
|
||||
0xe00ae278, 0xe90dd2ee, 0xf2048354, 0xfb03b3c2,
|
||||
0x1f672661, 0x166016f7, 0x0d69474d, 0x046e77db,
|
||||
0x1ed16a4a, 0x17d65adc, 0x0cdf0b66, 0x05d83bf0,
|
||||
0xe1bcae53, 0xe8bb9ec5, 0xf3b2cf7f, 0xfab5ffe9,
|
||||
0x1dbdf21c, 0x14bac28a, 0x0fb39330, 0x06b4a3a6,
|
||||
0xe2d03605, 0xebd70693, 0xf0de5729, 0xf9d967bf,
|
||||
0xe3667a2e, 0xea614ab8, 0xf1681b02, 0xf86f2b94,
|
||||
0x1c0bbe37, 0x150c8ea1, 0x0e05df1b, 0x0702ef8d,
|
||||
};
|
||||
|
||||
unsigned long zip_updcrc(icrc, icp, icnt)
|
||||
unsigned long icrc;
|
||||
unsigned char *icp;
|
||||
int icnt;
|
||||
{
|
||||
#define M1 0xffffff
|
||||
#define M2 0xffffff00
|
||||
register unsigned long crc = icrc;
|
||||
register unsigned char *cp = icp;
|
||||
register int cnt = icnt;
|
||||
|
||||
while(cnt--) {
|
||||
crc=((crc>>8)&M1)^crctab[(crc&0xff)^*cp++];
|
||||
}
|
||||
|
||||
return(crc);
|
||||
}
|
||||
|
7
doc/README.crc
Executable file
7
doc/README.crc
Executable file
@ -0,0 +1,7 @@
|
||||
This code is based on the code described in README.ORIG.
|
||||
Changes are:
|
||||
1. A program (makecrc) will create the different C source
|
||||
files to do crc calculations.
|
||||
2. The crc calculation method of binhex is added.
|
||||
3. 32 bit crc's are added.
|
||||
|
193
doc/README.crc.orig
Executable file
193
doc/README.crc.orig
Executable file
@ -0,0 +1,193 @@
|
||||
/* updcrc(3), crc(1) - calculate crc polynomials
|
||||
*
|
||||
* Calculate, intelligently, the CRC of a dataset incrementally given a
|
||||
* buffer full at a time.
|
||||
*
|
||||
* Usage:
|
||||
* newcrc = updcrc( oldcrc, bufadr, buflen )
|
||||
* unsigned int oldcrc, buflen;
|
||||
* char *bufadr;
|
||||
*
|
||||
* Compiling with -DTEST creates a program to print the CRC of stdin to stdout.
|
||||
* Compile with -DMAKETAB to print values for crctab to stdout. If you change
|
||||
* the CRC polynomial parameters, be sure to do this and change
|
||||
* crctab's initial value.
|
||||
*
|
||||
* Notes:
|
||||
* Regards the data stream as an integer whose MSB is the MSB of the first
|
||||
* byte recieved. This number is 'divided' (using xor instead of subtraction)
|
||||
* by the crc-polynomial P.
|
||||
* XMODEM does things a little differently, essentially treating the LSB of
|
||||
* the first data byte as the MSB of the integer. Define SWAPPED to make
|
||||
* things behave in this manner.
|
||||
*
|
||||
* Author: Mark G. Mendel, 7/86
|
||||
* UUCP: ihnp4!umn-cs!hyper!mark, GEnie: mgm
|
||||
*/
|
||||
|
||||
/* The CRC polynomial.
|
||||
* These 4 values define the crc-polynomial.
|
||||
* If you change them, you must change crctab[]'s initial value to what is
|
||||
* printed by initcrctab() [see 'compile with -DMAKETAB' above].
|
||||
*/
|
||||
/* Value used by: CITT XMODEM ARC */
|
||||
#define P 0xA001 /* the poly: 0x1021 0x1021 A001 */
|
||||
#define INIT_CRC 0L /* init value: -1 0 0 */
|
||||
#define SWAPPED /* bit order: undef defined defined */
|
||||
#define W 16 /* bits in CRC:16 16 16 */
|
||||
|
||||
/* data type that holds a W-bit unsigned integer */
|
||||
#if W <= 16
|
||||
# define WTYPE unsigned short
|
||||
#else
|
||||
# define WTYPE unsigned long
|
||||
#endif
|
||||
|
||||
/* the number of bits per char: don't change it. */
|
||||
#define B 8
|
||||
|
||||
static WTYPE crctab[1<<B] = /* as calculated by initcrctab() */ {
|
||||
0x0, 0xc0c1, 0xc181, 0x140, 0xc301, 0x3c0, 0x280, 0xc241,
|
||||
0xc601, 0x6c0, 0x780, 0xc741, 0x500, 0xc5c1, 0xc481, 0x440,
|
||||
0xcc01, 0xcc0, 0xd80, 0xcd41, 0xf00, 0xcfc1, 0xce81, 0xe40,
|
||||
0xa00, 0xcac1, 0xcb81, 0xb40, 0xc901, 0x9c0, 0x880, 0xc841,
|
||||
0xd801, 0x18c0, 0x1980, 0xd941, 0x1b00, 0xdbc1, 0xda81, 0x1a40,
|
||||
0x1e00, 0xdec1, 0xdf81, 0x1f40, 0xdd01, 0x1dc0, 0x1c80, 0xdc41,
|
||||
0x1400, 0xd4c1, 0xd581, 0x1540, 0xd701, 0x17c0, 0x1680, 0xd641,
|
||||
0xd201, 0x12c0, 0x1380, 0xd341, 0x1100, 0xd1c1, 0xd081, 0x1040,
|
||||
0xf001, 0x30c0, 0x3180, 0xf141, 0x3300, 0xf3c1, 0xf281, 0x3240,
|
||||
0x3600, 0xf6c1, 0xf781, 0x3740, 0xf501, 0x35c0, 0x3480, 0xf441,
|
||||
0x3c00, 0xfcc1, 0xfd81, 0x3d40, 0xff01, 0x3fc0, 0x3e80, 0xfe41,
|
||||
0xfa01, 0x3ac0, 0x3b80, 0xfb41, 0x3900, 0xf9c1, 0xf881, 0x3840,
|
||||
0x2800, 0xe8c1, 0xe981, 0x2940, 0xeb01, 0x2bc0, 0x2a80, 0xea41,
|
||||
0xee01, 0x2ec0, 0x2f80, 0xef41, 0x2d00, 0xedc1, 0xec81, 0x2c40,
|
||||
0xe401, 0x24c0, 0x2580, 0xe541, 0x2700, 0xe7c1, 0xe681, 0x2640,
|
||||
0x2200, 0xe2c1, 0xe381, 0x2340, 0xe101, 0x21c0, 0x2080, 0xe041,
|
||||
0xa001, 0x60c0, 0x6180, 0xa141, 0x6300, 0xa3c1, 0xa281, 0x6240,
|
||||
0x6600, 0xa6c1, 0xa781, 0x6740, 0xa501, 0x65c0, 0x6480, 0xa441,
|
||||
0x6c00, 0xacc1, 0xad81, 0x6d40, 0xaf01, 0x6fc0, 0x6e80, 0xae41,
|
||||
0xaa01, 0x6ac0, 0x6b80, 0xab41, 0x6900, 0xa9c1, 0xa881, 0x6840,
|
||||
0x7800, 0xb8c1, 0xb981, 0x7940, 0xbb01, 0x7bc0, 0x7a80, 0xba41,
|
||||
0xbe01, 0x7ec0, 0x7f80, 0xbf41, 0x7d00, 0xbdc1, 0xbc81, 0x7c40,
|
||||
0xb401, 0x74c0, 0x7580, 0xb541, 0x7700, 0xb7c1, 0xb681, 0x7640,
|
||||
0x7200, 0xb2c1, 0xb381, 0x7340, 0xb101, 0x71c0, 0x7080, 0xb041,
|
||||
0x5000, 0x90c1, 0x9181, 0x5140, 0x9301, 0x53c0, 0x5280, 0x9241,
|
||||
0x9601, 0x56c0, 0x5780, 0x9741, 0x5500, 0x95c1, 0x9481, 0x5440,
|
||||
0x9c01, 0x5cc0, 0x5d80, 0x9d41, 0x5f00, 0x9fc1, 0x9e81, 0x5e40,
|
||||
0x5a00, 0x9ac1, 0x9b81, 0x5b40, 0x9901, 0x59c0, 0x5880, 0x9841,
|
||||
0x8801, 0x48c0, 0x4980, 0x8941, 0x4b00, 0x8bc1, 0x8a81, 0x4a40,
|
||||
0x4e00, 0x8ec1, 0x8f81, 0x4f40, 0x8d01, 0x4dc0, 0x4c80, 0x8c41,
|
||||
0x4400, 0x84c1, 0x8581, 0x4540, 0x8701, 0x47c0, 0x4680, 0x8641,
|
||||
0x8201, 0x42c0, 0x4380, 0x8341, 0x4100, 0x81c1, 0x8081, 0x4040,
|
||||
} ;
|
||||
|
||||
WTYPE
|
||||
updcrc( icrc, icp, icnt )
|
||||
WTYPE icrc;
|
||||
unsigned char *icp;
|
||||
int icnt;
|
||||
{
|
||||
register WTYPE crc = icrc;
|
||||
register unsigned char *cp = icp;
|
||||
register int cnt = icnt;
|
||||
|
||||
while( cnt-- ) {
|
||||
#ifndef SWAPPED
|
||||
crc = (crc<<B) ^ crctab[(crc>>(W-B)) ^ *cp++];
|
||||
#else
|
||||
crc = (crc>>B) ^ crctab[(crc & ((1<<B)-1)) ^ *cp++];
|
||||
#endif SWAPPED
|
||||
}
|
||||
|
||||
return( crc );
|
||||
}
|
||||
|
||||
#ifdef MAKETAB
|
||||
|
||||
#include <stdio.h>
|
||||
main()
|
||||
{
|
||||
initcrctab();
|
||||
}
|
||||
|
||||
initcrctab()
|
||||
{
|
||||
register int b, i;
|
||||
WTYPE v;
|
||||
|
||||
|
||||
for( b = 0; b <= (1<<B)-1; ++b ) {
|
||||
#ifndef SWAPPED
|
||||
for( v = b<<(W-B), i = B; --i >= 0; )
|
||||
v = v & ((WTYPE)1<<(W-1)) ? (v<<1)^P : v<<1;
|
||||
#else
|
||||
for( v = b, i = B; --i >= 0; )
|
||||
v = v & 1 ? (v>>1)^P : v>>1;
|
||||
#endif
|
||||
crctab[b] = v;
|
||||
|
||||
printf( "0x%lx,", v & ((1L<<W)-1L));
|
||||
if( (b&7) == 7 )
|
||||
printf("\n" );
|
||||
else
|
||||
printf(" ");
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef TEST
|
||||
|
||||
#include <stdio.h>
|
||||
#include <fcntl.h>
|
||||
|
||||
#define MAXBUF 4096
|
||||
|
||||
|
||||
|
||||
main( ac, av )
|
||||
int ac; char **av;
|
||||
{
|
||||
int fd;
|
||||
int nr;
|
||||
int i;
|
||||
char buf[MAXBUF];
|
||||
WTYPE crc, crc2;
|
||||
|
||||
fd = 0;
|
||||
if( ac > 1 )
|
||||
if( (fd = open( av[1], O_RDONLY )) < 0 ) {
|
||||
perror( av[1] );
|
||||
exit( -1 );
|
||||
}
|
||||
crc = crc2 = INIT_CRC;
|
||||
|
||||
while( (nr = read( fd, buf, MAXBUF )) > 0 ) {
|
||||
crc = updcrc( crc, buf, nr );
|
||||
}
|
||||
|
||||
if( nr != 0 )
|
||||
perror( "reading" );
|
||||
else {
|
||||
printf( "%lx\n", crc );
|
||||
}
|
||||
|
||||
#ifdef MAGICCHECK
|
||||
/* tack one's complement of crc onto data stream, and
|
||||
continue crc calculation. Should get a constant (magic number)
|
||||
dependent only on P, not the data.
|
||||
*/
|
||||
crc2 = crc ^ -1L;
|
||||
for( nr = W-B; nr >= 0; nr -= B ) {
|
||||
buf[0] = (crc2 >> nr);
|
||||
crc = updcrc(crc, buf, 1);
|
||||
}
|
||||
|
||||
/* crc should now equal magic */
|
||||
buf[0] = buf[1] = buf[2] = buf[3] = 0;
|
||||
printf( "magic test: %lx =?= %lx\n", crc, updcrc(-1, buf, W/B));
|
||||
#endif MAGICCHECK
|
||||
}
|
||||
|
||||
#endif
|
||||
****************************************************************************
|
||||
|
31
doc/README.hexbin
Executable file
31
doc/README.hexbin
Executable file
@ -0,0 +1,31 @@
|
||||
The comment for the predecessor of hexbin.
|
||||
|
||||
/*
|
||||
* xbin -- unpack BinHex format file into suitable
|
||||
* format for downloading with macput
|
||||
* Dave Johnson, Brown University Computer Science
|
||||
*
|
||||
* (c) 1984 Brown University
|
||||
* may be used but not sold without permission
|
||||
*
|
||||
* created ddj 12/16/84
|
||||
* revised ddj 03/10/85 -- version 4.0 compatibility, other minor mods
|
||||
* revised ddj 03/11/85 -- strip LOCKED bit from m_flags
|
||||
* revised ahm 03/12/85 -- System V compatibility
|
||||
* revised dba 03/16/85 -- (Darin Adler, TMQ Software) 4.0 EOF fixed,
|
||||
* 4.0 checksum added
|
||||
* revised ddj 03/17/85 -- extend new features to older formats: -l, stdin
|
||||
* revised ddj 03/24/85 -- check for filename truncation, allow multiple files
|
||||
* revised ddj 03/26/85 -- fixed USG botches, many problems w/multiple files
|
||||
* revised jcb 03/30/85 -- (Jim Budler, amdcad!jimb), revised for compatibility
|
||||
* with 16-bit int machines
|
||||
* revised dl 06/16/85 -- (Dan LaLiberte, liberte@uiucdcs) character
|
||||
* translation speedup
|
||||
* revised ddj 09/30/85 -- fixed problem with run of RUNCHAR
|
||||
* revised gvr 11/15/86 -- speed-up: rewrote .hqx decoding (mcvax!guido)
|
||||
* revised jwm 04/26/88 -- now recognizes "(Convert with" as a starting line
|
||||
* -- the widely-used Stuffit uses this as a header
|
||||
* revised dtw ../../89 -- hqx format will skip garbage lines; undoes some of
|
||||
* -- gvr's work. will now also recognize .dl format.
|
||||
*/
|
||||
|
14
doc/README.macget
Executable file
14
doc/README.macget
Executable file
@ -0,0 +1,14 @@
|
||||
/*
|
||||
* macget -- receive file from macintosh using xmodem protocol
|
||||
* Dave Johnson, Brown University Computer Science
|
||||
*
|
||||
* (c) 1984 Brown University
|
||||
* may be used but not sold without permission
|
||||
*
|
||||
* created ddj 5/22/84
|
||||
* revised ddj 6/29/84 -- added [-rdu] options
|
||||
* revised ddj 7/16/84 -- protocol changes for MacTerminal Beta Version 0.5X
|
||||
* revised ddj 7/31/84 -- pre-4.2 signal bugs fixed in timedout()
|
||||
* revised ddj 11/7/84 -- renamed send_sync() -> get_sync()
|
||||
* revised lra 1/01/87 -- multiple file uploads added (VersTerm compatible)
|
||||
*/
|
18
doc/README.macput
Executable file
18
doc/README.macput
Executable file
@ -0,0 +1,18 @@
|
||||
/*
|
||||
*
|
||||
* Here is the source for the current incarnation of macput . . . .
|
||||
* It is compatible with the 1.1 Release version of MacTerminal,
|
||||
* though in case you still need to use the -0.15X version, there's
|
||||
* the "-o" option to provide compatibility. Versions 0.5 and 0.9
|
||||
* have a bug in the record checksum calculation which will break
|
||||
* file transfers, so 1.1 is recommended.
|
||||
*
|
||||
* Please pass any improvements/bug fixes on to me, and
|
||||
* if you know of any good protocols for use on a flow-controlled
|
||||
* line, let me know.
|
||||
*
|
||||
* Dave Johnson
|
||||
* ddj%brown@csnet-relay.arpa
|
||||
* Brown University Computer Science
|
||||
*
|
||||
*/
|
92
doc/README.scan
Executable file
92
doc/README.scan
Executable file
@ -0,0 +1,92 @@
|
||||
Preliminary info about the Unix scanner.
|
||||
----------------------------------------
|
||||
|
||||
This file states mostly how to use it, it is not yet full documentation.
|
||||
|
||||
There are a few utilities in this package that help scanning: macidf,
|
||||
macscan, macstream, hexbin and macunpack. I will give examples of use
|
||||
where every use highlights some factilities.
|
||||
|
||||
The main program is macscan. It reads from standard input (NB: no file
|
||||
parameters) and will scan the input for offensive stuff. The input
|
||||
consists of a stream of files in MacBinary format, with additional
|
||||
information between (about Unix file name, Archive/Packed file name,
|
||||
folder entry/exit in an archive etc.).
|
||||
|
||||
To scan a single MacBinary file just do:
|
||||
macscan <file
|
||||
This will read the file and macscan will mark everything it does not like.
|
||||
Also when macscan detects that it is an archive, it will unpack the archive,
|
||||
and recursively so for embedded archives. When given the opion -l macscan
|
||||
will list the contents of the archive during its scan. When given the
|
||||
option -v it will also list all resources found, with type, number,
|
||||
name (if defined) and size.
|
||||
|
||||
If you have multiple MacBinary files (e.g. a set of MacBinary files in a
|
||||
directory tree), you can do the following (supposing the filenames end in
|
||||
'.bin'):
|
||||
find directory -name '*.bin' -exec xxx {} \; | macscan
|
||||
Where xxx is the following shellscript:
|
||||
#!/bin/sh
|
||||
macidf $1
|
||||
cat $1
|
||||
The macidf is needed so that macscan knows the original Unix file name.
|
||||
Of course macscan can also get the -l and -v options.
|
||||
|
||||
If you have a directory tree with binhexed files, the following is
|
||||
appropriate:
|
||||
find directory -name '*.hqx' -exec hexbin -S {} \; | macscan
|
||||
The flag -S tells hexbin that filename info for macscan must be included.
|
||||
And here again, macscan can have options. Note: every binhexed file must
|
||||
be contained in a single Unix file, unlike mcvert. But, like mcvert,
|
||||
mailheaders and such can preceed and follow the binhexed file, and can
|
||||
also be in the middle.
|
||||
|
||||
You can of course have compressed binhexed files, in that case:
|
||||
find directory -name '*.hqx.Z' -exec xxx {} \; | macscan
|
||||
with xxx the following shellscript:
|
||||
#!/bin/sh
|
||||
macidf $1
|
||||
zcat $1 | hexbin -s
|
||||
(Note, lower case s here. Hexbin has no knowledge about the Unix filename.)
|
||||
|
||||
If the directory is an AUFS directory the following can be done:
|
||||
macstream directory | macscan
|
||||
Note: in this case it is not yet possible to include the Unix filename in
|
||||
the output of macscan. With the option -l Mac names are listed.
|
||||
|
||||
The previous method might also work with AppleDouble directories, but I am
|
||||
not sure about that.
|
||||
|
||||
-------
|
||||
What macscan can at this moment.
|
||||
|
||||
It currently uses a subset of Jeff's VirusDetective strings during the scan.
|
||||
Not all strings are yet implemented, so not all viruses are already detected.
|
||||
|
||||
Moreover, it includes warnings for CDEF 0, WDEF 0 etc. resources, as per
|
||||
Zig's suggestion.
|
||||
|
||||
Finally, it warns about resources compressed by the resource compressor of
|
||||
Ben Haller.
|
||||
|
||||
-------
|
||||
The status.
|
||||
|
||||
This version is preliminary and confidential. Do not distribute.
|
||||
There are probably a number of bugs present, although my testing
|
||||
on a Sun (actually an FPS == very fast Sun) worked pretty well.
|
||||
Lint does not complain too much ;-). Also SGI's lint has not
|
||||
many problems with it. Mostly because the difference between
|
||||
(char *)malloc();
|
||||
and
|
||||
(void *)malloc();
|
||||
etc. That must be straightened out sometime.
|
||||
|
||||
Any bug-reports, suggestions are wellcome. Please support bug-reports
|
||||
with input or somesuch.
|
||||
|
||||
dik
|
||||
--
|
||||
dik t. winter, cwi, kruislaan 413, 1098 sj amsterdam, nederland
|
||||
dik@cwi.nl
|
62
doc/README.unpit
Executable file
62
doc/README.unpit
Executable file
@ -0,0 +1,62 @@
|
||||
/*
|
||||
* @(#)unpit.c 1.2 (CWI) 87/11/05
|
||||
*/
|
||||
|
||||
/*
|
||||
|
||||
unpit - Macintosh PackIt file unpacker
|
||||
|
||||
Version 2, for PackIt II
|
||||
|
||||
This program will unpack a Macintosh PackIt file into separate files. The
|
||||
data fork of a PackIt file contains both the data and resource forks of the
|
||||
packed files. The program will unpack each Mac file into separate .data,
|
||||
.rsrc., and .info files that can be downloaded to a Mac using macput.
|
||||
|
||||
The program syntax is much like macput/macget:
|
||||
|
||||
unpit [-rdu] packit-file.data
|
||||
|
||||
The -r and -d flags will cause only the resource and data forks to be
|
||||
written. The -u flag will cause only the data fork to be written and
|
||||
to have carriage return characters changed to Unix newline characters.
|
||||
|
||||
Some of the program is borrowed from the macput.c/macget.c programs.
|
||||
|
||||
Author: Allan G. Weber, (Weber%Brand@USC-ECL)
|
||||
Date: September 30, 1985
|
||||
Revised: January 24, 1986 - added CRC checking
|
||||
March 25, 1986 - support compressed mode of PackIt II,
|
||||
check for illegal Unix file names
|
||||
|
||||
*/
|
||||
|
||||
/* There is some confusion as to what to do with the "inited" flag in the
|
||||
finder info bytes that are in the header of each file in the packit file.
|
||||
If this flag bit is copied to the .info file, it seems to confuse
|
||||
MacTerminal into placing the file icons in the upper left corner of the
|
||||
window on top of each other. Setting this bit to zero in the .info file
|
||||
seems to fix that problem but may cause others. I haven't been able to
|
||||
find any .info files that have this flag set so making it zero may be OK.
|
||||
Anyway, MacTerminal seems to set the flag when it create the file on the
|
||||
Mac. The "#define INITED_BUG" can be used to try both settings. */
|
||||
|
||||
/*
|
||||
Format of a Packit file:
|
||||
|
||||
Repeat the following sequence for each file in the Packit file:
|
||||
|
||||
4 byte identifier ("PMag" = not compressed, "Pma4" = compressed)
|
||||
variable length compression data (if compressed file)
|
||||
92 byte header (see struct pit_header below) *
|
||||
2 bytes CRC number *
|
||||
data fork (length from header) *
|
||||
resource fork (length from header) *
|
||||
2 bytes CRC number *
|
||||
|
||||
Last file is followed by the 4 byte Ascii string, "Pend", and then the EOF.
|
||||
|
||||
* these are in compressed form if compression is on for the file
|
||||
|
||||
*/
|
||||
|
46
doc/README.unsit
Executable file
46
doc/README.unsit
Executable file
@ -0,0 +1,46 @@
|
||||
/*
|
||||
unsit - Macintosh StuffIt file extractor
|
||||
|
||||
Version 1, for StuffIt 1.31
|
||||
|
||||
This program will unpack a Macintosh StuffIt file into separate files.
|
||||
The data fork of a StuffIt file contains both the data and resource
|
||||
forks of the packed files. The program will unpack each Mac file into
|
||||
separate .data, .rsrc., and .info files that can be downloaded to a
|
||||
Mac using macput. The program is much like the "unpit" program for
|
||||
breaking apart Packit archive files.
|
||||
|
||||
***** IMPORTANT *****
|
||||
To extract StuffIt files that have been compressed with the Lempel-Ziv
|
||||
compression method, unsit pipes the data through the "compress"
|
||||
program with the appropriate switches, rather than incorporate the
|
||||
uncompression routines within "unsit". Therefore, it is necessary to
|
||||
have the "compress" program on the system and in the search path to
|
||||
make "unsit" work. "Compress" is available from the comp.sources.unix
|
||||
archives.
|
||||
|
||||
The program syntax is much like unpit and macput/macget, with some added
|
||||
options:
|
||||
|
||||
unsit [-rdulvq] stuffit-file.data
|
||||
|
||||
The -r and -d flags will cause only the resource and data forks to be
|
||||
written. The -u flag will cause only the data fork to be written and
|
||||
to have carriage return characters changed to Unix newline characters.
|
||||
The -l flag will make the program only list the files in the StuffIt
|
||||
file. The -v flag causes the program to list the names, sizes, type,
|
||||
and creators of the files it is writing. The -q flag causes it to
|
||||
list the name, type and size of each file and wait for a 'y' or 'n'
|
||||
for either writing that file or skipping it, respectively.
|
||||
|
||||
Some of the program is borrowed from the macput.c/macget.c programs.
|
||||
Many, many thanks to Raymond Lau, the author of StuffIt, for including
|
||||
information on the format of the StuffIt archives in the documentation.
|
||||
|
||||
Author: Allan G. Weber
|
||||
weber%brand.usc.edu@oberon.usc.edu
|
||||
...sdcrdcf!usc-oberon!brand!weber
|
||||
Date: January 15, 1988
|
||||
|
||||
*/
|
||||
|
101
doc/README.zoom
Executable file
101
doc/README.zoom
Executable file
@ -0,0 +1,101 @@
|
||||
Taken from the file plugins.h in the Zoom distribution.
|
||||
|
||||
/*
|
||||
* The Zoom archive format is:
|
||||
*
|
||||
* (char) Magic1
|
||||
* (char) Magic2 - or - (char) Magic2B
|
||||
* (char) Magic3
|
||||
* (char) Magic4
|
||||
*
|
||||
* IF Magic2B was received THEN
|
||||
* (long) logicalEof /* For multi-file archives * /
|
||||
* END IF
|
||||
*
|
||||
* <EntryChain>
|
||||
*
|
||||
* The format of <EntryChain> is a linked list of
|
||||
* EntryInfo, where "next" points to the next logical address
|
||||
* on disk. "next" as 0 means no more entries.
|
||||
*
|
||||
* For a directory, the "creator" field points to the
|
||||
* first file/folder entry inside the directory.
|
||||
*
|
||||
* For a file, IF the "what" field is ZOOM_PLUGIN,
|
||||
* the EntryInfo is followed by a length byte and that
|
||||
* many characters naming the compression engine.
|
||||
* Right after that (or right after the EntryInfo in the
|
||||
* case of uncompressed files or default compressed files)
|
||||
* follows the data fork compressed, followed by the
|
||||
* resource fork compressed.
|
||||
*
|
||||
* Note that there is no "end of compressed data" marker;
|
||||
* your compressor engine will have to figure that out by
|
||||
* itself. You could for instance do an ftell before
|
||||
* compressing; writing a (long)0 and then write your
|
||||
* compressed data, seek back and write the actual length.
|
||||
*
|
||||
* Note that new entries always are added last in the file,
|
||||
* so you need not worry about overrunning anything else.
|
||||
*/
|
||||
|
||||
/*
|
||||
* The default compressor in Zoom is the same as used in
|
||||
* "better" compression mode in ZOO 2.10. A Zoo extractor
|
||||
* or convertor could parse the ZOO header format, and use
|
||||
* the built-in engine for "lzh" compressed files.
|
||||
*
|
||||
* The simplest way to do this is to call SetEngine(-1) and
|
||||
* call Encode / Decode. -1 is the default compressor, 0 is
|
||||
* the null compressor (fork copy)
|
||||
*
|
||||
* Likewise, a UNIX zoom packer/unpacker could use the source
|
||||
* for zoo 2.10 functions "lzh_encode" and "lzh_decode"
|
||||
* (they're wrappers) for compression.
|
||||
*/
|
||||
|
||||
/*
|
||||
* This "EntryInfo" is presently also a file header.
|
||||
* Some fields may be non-obvious. Don't use these.
|
||||
* For instance, "comment" is currently unsupported,
|
||||
* and should be left as 0
|
||||
*/
|
||||
#ifndef ZOOM_TYPES
|
||||
typedef enum zoomWhatType {
|
||||
ZOOM_NOTHING , ZOOM_FILE , ZOOM_UCFILE , ZOOM_DIR , ZOOM_PLUGIN
|
||||
} ZoomWhatType ;
|
||||
#define ZOOM_TYPES
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Remember to fill in "hlen" correctly as well. When reading a header,
|
||||
* Zoom checks with this field to see if it should skip some more data
|
||||
* or seek back a little, so as to make future field additions at the
|
||||
* end possible. You should NOT add your own fields to this structure.
|
||||
*/
|
||||
typedef struct EntryInfo {
|
||||
|
||||
/* "what" is a ZoomWhatType */
|
||||
char what ; /* Negative if deleted */
|
||||
unsigned char hlen ; /* Header length */
|
||||
unsigned short boolFlags ; /* Boolean flags */
|
||||
long next ; /* Next entry */
|
||||
|
||||
long complen ; /* Length of compressed data */
|
||||
long compdata ; /* Data fork portion of compressed data - for dirs, number of entries */
|
||||
long uclen ; /* Length of uncompressed entry */
|
||||
long ucdata ; /* Data fork part of uncompressed */
|
||||
|
||||
long type ; /* File type */
|
||||
long creator ; /* File creator - for dir, offset of file */
|
||||
long mdate ; /* Modification date */
|
||||
long comment ; /* Comment offset */
|
||||
short flags ; /* Macintosh file flags */
|
||||
|
||||
short dataCrc ; /* Data fork crc */
|
||||
short resCrc ; /* Resource fork crc */
|
||||
|
||||
unsigned char name [ 32 ] ; /* File/Dir name */
|
||||
|
||||
} EntryInfo ;
|
||||
|
0
fileio/all
Normal file
0
fileio/all
Normal file
53
fileio/appledouble.h
Executable file
53
fileio/appledouble.h
Executable file
@ -0,0 +1,53 @@
|
||||
#define FI_MAGIC 333319
|
||||
#define FI_VERSION 1
|
||||
#define FI_FILL5 5
|
||||
#define FI_FILL6 2
|
||||
#define FI_HLEN 589
|
||||
#define FI_FILL7 3
|
||||
#define FI_NAMPTR 86
|
||||
#define FI_FILL9 4
|
||||
#define FI_COMMPTR 341
|
||||
#define FI_FILL12 7
|
||||
#define FI_TIMEPTR 541
|
||||
#define FI_TIMESIZE 16
|
||||
#define FI_FILL15 9
|
||||
#define FI_INFOPTR 557
|
||||
#define FI_INFOSIZE 32
|
||||
|
||||
/* All as char[n] because of possible alignment problems. But is this needed?
|
||||
Is this stuff in host order or in client order? Assuming client order for
|
||||
the moment. Will not be a problem on big-endian machines. */
|
||||
typedef struct {
|
||||
char fi_magic[4]; /* magic header */
|
||||
char fi_version[2]; /* version number */
|
||||
char fi_fill1[4]; /* = 0, ???? */
|
||||
char fi_fill2[4]; /* = 0, ???? */
|
||||
char fi_fill3[4]; /* = 0, ???? */
|
||||
char fi_fill4[4]; /* = 0, ???? */
|
||||
char fi_fill5[4]; /* = 5, ???? */
|
||||
char fi_fill6[4]; /* = 2, ???? */
|
||||
char fi_hlen[4]; /* = 589, header length */
|
||||
char fi_rsrc[4]; /* resource length */
|
||||
char fi_fill7[4]; /* = 3, ???? */
|
||||
char fi_namptr[4]; /* = 86, filename pointer */
|
||||
char fi_namlen[4]; /* Mac filename length */
|
||||
char fi_fill9[4]; /* = 4, ???? */
|
||||
char fi_commptr[4]; /* = 341, comment pointer */
|
||||
char fi_commsize[4]; /* = 0, comment size */
|
||||
char fi_fill12[4]; /* = 7, ???? */
|
||||
char fi_timeptr[4]; /* = 541, pointer to times */
|
||||
char fi_timesize[4]; /* = 16, size of times */
|
||||
char fi_fill15[4]; /* = 9, ???? */
|
||||
char fi_infoptr[4]; /* = 557, finder info pointer */
|
||||
char fi_infosize[4]; /* = 32, finder info size */
|
||||
char fi_name[255]; /* Macintosh filename */
|
||||
char fi_comment[200];/* = 0, Comment */
|
||||
char fi_ctime[4]; /* Creation time (Unix time) */
|
||||
char fi_mtime[4]; /* Modification time (Unix time) */
|
||||
char fi_fill19[4]; /* = 0, ???? */
|
||||
char fi_fill20[4]; /* = 0, ???? */
|
||||
char fi_type[4]; /* File type */
|
||||
char fi_auth[4]; /* File creator */
|
||||
char fi_finfo[24]; /* Finder info */
|
||||
} FileInfo;
|
||||
|
33
fileio/aufs.h
Executable file
33
fileio/aufs.h
Executable file
@ -0,0 +1,33 @@
|
||||
#define MAXCLEN 199 /* max size of a comment string */
|
||||
#define FINFOLEN 32 /* Finder info is 32 bytes */
|
||||
#define MAXMACFLEN 31 /* max Mac file name length */
|
||||
#define FI_MAGIC1 255
|
||||
#define FI_VERSION 0x10 /* version major 1, minor 0 */
|
||||
/* if we have more than 8 versions wer're */
|
||||
/* doiong something wrong anyway */
|
||||
#define FI_MAGIC 0xda
|
||||
#define FI_BM_SHORTFILENAME 0x1 /* is this included? */
|
||||
#define FI_BM_MACINTOSHFILENAME 0x2 /* is this included? */
|
||||
#define FI_MDATE 0x01 /* mtime & utime are valid */
|
||||
#define FI_CDATE 0x02 /* ctime is valid */
|
||||
|
||||
typedef struct {
|
||||
char fi_fndr[FINFOLEN]; /* finder info */
|
||||
short fi_attr; /* attributes */
|
||||
char fi_magic1; /* addional magic word check */
|
||||
char fi_version; /* version number */
|
||||
char fi_magic; /* magic word check */
|
||||
char fi_bitmap; /* bitmap of included info */
|
||||
char fi_shortfilename[12+1]; /* possible short file name */
|
||||
char fi_macfilename[32+1]; /* possible macintosh file name */
|
||||
char fi_comln; /* comment length */
|
||||
char fi_comnt[MAXCLEN+1]; /* comment string */
|
||||
#ifdef AUFSPLUS
|
||||
char fi_datemagic; /* sanity check */
|
||||
char fi_datevalid; /* validity flags */
|
||||
char fi_ctime[4]; /* mac file create time */
|
||||
char fi_mtime[4]; /* mac file modify time */
|
||||
char fi_utime[4]; /* (real) time mtime was set */
|
||||
#endif /* AUFSPLUS */
|
||||
} FileInfo;
|
||||
|
2
fileio/fileglob.c
Executable file
2
fileio/fileglob.c
Executable file
@ -0,0 +1,2 @@
|
||||
int bytes_read, bytes_written;
|
||||
|
2
fileio/fileglob.h
Executable file
2
fileio/fileglob.h
Executable file
@ -0,0 +1,2 @@
|
||||
extern int bytes_read, bytes_written;
|
||||
|
BIN
fileio/fileglob.o
Normal file
BIN
fileio/fileglob.o
Normal file
Binary file not shown.
10
fileio/kind.h
Executable file
10
fileio/kind.h
Executable file
@ -0,0 +1,10 @@
|
||||
#ifdef SCAN
|
||||
#define UNIX_NAME 0
|
||||
#define PACK_NAME 1
|
||||
#define ARCH_NAME 2
|
||||
#define UNKNOWN 16
|
||||
#define PROTECTED 17
|
||||
#define ERROR 32
|
||||
#define COPY 33
|
||||
#endif /* SCAN */
|
||||
|
20
fileio/machdr.h
Executable file
20
fileio/machdr.h
Executable file
@ -0,0 +1,20 @@
|
||||
#define INFOBYTES 128
|
||||
|
||||
/* The following are copied out of macput.c/macget.c */
|
||||
#define I_NAMEOFF 1
|
||||
/* 65 <-> 80 is the FInfo structure */
|
||||
#define I_TYPEOFF 65
|
||||
#define I_AUTHOFF 69
|
||||
#define I_FLAGOFF 73
|
||||
#define I_LOCKOFF 81
|
||||
#define I_DLENOFF 83
|
||||
#define I_RLENOFF 87
|
||||
#define I_CTIMOFF 91
|
||||
#define I_MTIMOFF 95
|
||||
|
||||
#define F_NAMELEN 63
|
||||
#define I_NAMELEN 69 /* 63 + strlen(".info") + 1 */
|
||||
|
||||
#define INITED_MASK 1
|
||||
#define PROTCT_MASK 0x40
|
||||
|
33
fileio/makefile
Executable file
33
fileio/makefile
Executable file
@ -0,0 +1,33 @@
|
||||
CFLAGS= -O $(CF)
|
||||
|
||||
all: wrfile.o rdfile.o fileglob.o
|
||||
touch all
|
||||
|
||||
wrfile.o: wrfile.c
|
||||
|
||||
rdfile.o: rdfile.c
|
||||
|
||||
clean:
|
||||
-rm -f wrfile.o
|
||||
-rm -f rdfile.o
|
||||
-rm -f fileglob.o
|
||||
-rm -f all
|
||||
|
||||
wrfile.o: machdr.h
|
||||
wrfile.o: wrfile.h
|
||||
wrfile.o: wrfileopt.h
|
||||
wrfile.o: fileglob.h
|
||||
wrfile.o: aufs.h
|
||||
wrfile.o: appledouble.h
|
||||
wrfile.o: ../util/util.h
|
||||
wrfile.o: ../util/curtime.h
|
||||
rdfile.o: machdr.h
|
||||
rdfile.o: rdfile.h
|
||||
rdfile.o: rdfileopt.h
|
||||
rdfile.o: ../util/util.h
|
||||
rdfile.o: ../util/curtime.h
|
||||
rdfile.o: ../util/masks.h
|
||||
rdfile.o: aufs.h
|
||||
rdfile.o: appledouble.h
|
||||
fileglob.o: fileglob.h
|
||||
|
1010
fileio/rdfile.c
Executable file
1010
fileio/rdfile.c
Executable file
File diff suppressed because it is too large
Load Diff
13
fileio/rdfile.h
Executable file
13
fileio/rdfile.h
Executable file
@ -0,0 +1,13 @@
|
||||
#define ISATEND 0
|
||||
#define ISFILE 1
|
||||
#define ISDIR 2
|
||||
#define ENDDIR 3
|
||||
|
||||
extern char file_info[INFOBYTES];
|
||||
extern char *data_fork, *rsrc_fork;
|
||||
extern int data_size, rsrc_size;
|
||||
|
||||
extern void setup();
|
||||
extern int nextfile();
|
||||
extern char *get_minb();
|
||||
|
BIN
fileio/rdfile.o
Normal file
BIN
fileio/rdfile.o
Normal file
Binary file not shown.
5
fileio/rdfileopt.h
Executable file
5
fileio/rdfileopt.h
Executable file
@ -0,0 +1,5 @@
|
||||
extern int rdfileopt();
|
||||
extern void give_rdfileopt();
|
||||
extern void set_norecurse();
|
||||
extern char *get_rdfileopt();
|
||||
|
847
fileio/wrfile.c
Executable file
847
fileio/wrfile.c
Executable file
@ -0,0 +1,847 @@
|
||||
#ifdef TYPES_H
|
||||
#include <sys/types.h>
|
||||
#endif /* TYPES_H */
|
||||
#include <sys/stat.h>
|
||||
#include <ctype.h>
|
||||
#include <stdio.h>
|
||||
#include "machdr.h"
|
||||
#include "wrfile.h"
|
||||
#include "wrfileopt.h"
|
||||
#include "../util/util.h"
|
||||
#ifdef AUFSPLUS
|
||||
#include "../util/curtime.h"
|
||||
#define AUFS
|
||||
#endif /* AUFSPLUS */
|
||||
#ifdef AUFS
|
||||
#include "aufs.h"
|
||||
#define APPLESHARE
|
||||
#endif /* AUFS */
|
||||
#ifdef APPLEDOUBLE
|
||||
#include "appledouble.h"
|
||||
#include "../util/curtime.h"
|
||||
#define APPLESHARE
|
||||
#endif /* APPLEDOUBLE */
|
||||
|
||||
#define TEXT 0
|
||||
#define DATA 1
|
||||
#define RSRC 2
|
||||
#define FULL 3
|
||||
#define MACB 4
|
||||
#define FORK 5
|
||||
#define APSH 6
|
||||
#define MACS 7
|
||||
#define UNIX 8
|
||||
#ifdef SCAN
|
||||
#define MACI 9
|
||||
#endif /* SCAN */
|
||||
|
||||
extern char *malloc();
|
||||
extern char *realloc();
|
||||
extern char *strcpy();
|
||||
extern char *strncpy();
|
||||
extern char *strcat();
|
||||
extern void exit();
|
||||
|
||||
#ifdef UNDEF /* Do not declare sprintf; not portable (but lint will complain) */
|
||||
char *sprintf();
|
||||
#endif /* UNDEF */
|
||||
|
||||
#ifdef AUFS
|
||||
static void check_aufs();
|
||||
static void aufs_namings();
|
||||
static void wr_aufs_info();
|
||||
#endif /* AUFS */
|
||||
#ifdef APPLEDOUBLE
|
||||
static void check_appledouble();
|
||||
static void appledouble_namings();
|
||||
static void wr_appledouble_info();
|
||||
#endif /* APPLEDOUBLE */
|
||||
#ifdef APPLESHARE
|
||||
static void mk_share_name();
|
||||
#endif /* APPLESHARE */
|
||||
|
||||
#ifndef BSD
|
||||
/* all those stupid differences! */
|
||||
#define bcopy(src,dest,length) memcpy((dest),(src),(length))
|
||||
#define bzero(block,length) memset((block),0,(length))
|
||||
#endif /* BSD */
|
||||
|
||||
#define INFO_FORK 1
|
||||
#define RSRC_FORK 2
|
||||
#define DATA_FORK 3
|
||||
|
||||
static char f_info[I_NAMELEN];
|
||||
static char f_data[I_NAMELEN*3];
|
||||
static char f_rsrc[I_NAMELEN];
|
||||
static char f_text[I_NAMELEN];
|
||||
static char f_unix[I_NAMELEN];
|
||||
static char f_bin[I_NAMELEN];
|
||||
static char f_folder[] = ".foldername";
|
||||
static char share_name[256];
|
||||
#ifdef APPLESHARE
|
||||
static char hex[] = "0123456789abcdef";
|
||||
#endif /* APPLESHARE */
|
||||
#ifdef AUFS
|
||||
static char infodir[] = ".finderinfo";
|
||||
static char rsrcdir[] = ".resource";
|
||||
#define INFOSZ sizeof(infodir)
|
||||
#define RSRCSZ sizeof(rsrcdir)
|
||||
static char f_info_aufs[I_NAMELEN*3+INFOSZ];
|
||||
static char f_rsrc_aufs[I_NAMELEN*3+RSRCSZ];
|
||||
#endif /* AUFS */
|
||||
#ifdef APPLEDOUBLE
|
||||
static char infodir[] = ".AppleDouble";
|
||||
#define INFOSZ sizeof(infodir)
|
||||
static char f_info_appledouble[I_NAMELEN*3+INFOSZ];
|
||||
#endif /* APPLEDOUBLE */
|
||||
|
||||
static int mode = MACB;
|
||||
static int mode_restricted = 0;
|
||||
static int mode_s_restricted = 0;
|
||||
char *out_buffer, *out_ptr;
|
||||
|
||||
static char init_buffer[128];
|
||||
static char *buffer = &(init_buffer[0]);
|
||||
static char *rbuffer = NULL, *dbuffer = NULL;
|
||||
static char *ptr;
|
||||
static unsigned long rsz, dsz, totsize, maxsize;
|
||||
|
||||
void define_name(text)
|
||||
char *text;
|
||||
{
|
||||
(void)sprintf(f_info, "%s.info", text);
|
||||
(void)sprintf(f_rsrc, "%s.rsrc", text);
|
||||
(void)sprintf(f_data, "%s.data", text);
|
||||
(void)sprintf(f_text, "%s.text", text);
|
||||
(void)sprintf(f_bin, "%s.bin", text);
|
||||
(void)sprintf(f_unix, "%s", text);
|
||||
#ifdef APPLESHARE
|
||||
/* Do not do namestuffing here. We want to base again on the information in
|
||||
the info header, so this is delayed
|
||||
*/
|
||||
#endif /* APPLESHARE */
|
||||
}
|
||||
|
||||
void start_info(info, rsize, dsize)
|
||||
char *info;
|
||||
unsigned long rsize, dsize;
|
||||
{
|
||||
int rs, ds;
|
||||
|
||||
rsz = rsize;
|
||||
dsz = dsize;
|
||||
rs = (((rsz + 127) >> 7) << 7);
|
||||
ds = (((dsz + 127) >> 7) << 7);
|
||||
totsize = rs + ds + 128;
|
||||
if(buffer == &(init_buffer[0])) {
|
||||
buffer = (char *)malloc((unsigned)totsize);
|
||||
} else if(maxsize < totsize) {
|
||||
buffer = (char *)realloc(buffer, (unsigned)totsize);
|
||||
}
|
||||
maxsize = totsize;
|
||||
if(buffer == NULL) {
|
||||
(void)fprintf(stderr, "Insufficient memory, aborting\n");
|
||||
exit(1);
|
||||
}
|
||||
dbuffer = buffer + 128;
|
||||
rbuffer = dbuffer + ds;
|
||||
(void)bzero(buffer, (int)totsize);
|
||||
ptr = buffer;
|
||||
(void)bcopy(info, ptr, 128);
|
||||
#ifdef AUFS
|
||||
/* Now we do filenaming etc. */
|
||||
if(mode == APSH) {
|
||||
aufs_namings();
|
||||
}
|
||||
#endif /* AUFS */
|
||||
#ifdef APPLEDOUBLE
|
||||
/* Now we do filenaming etc. */
|
||||
if(mode == APSH) {
|
||||
appledouble_namings();
|
||||
}
|
||||
#endif /* APPLEDOUBLE */
|
||||
}
|
||||
|
||||
void start_rsrc()
|
||||
{
|
||||
out_buffer = out_ptr = rbuffer;
|
||||
}
|
||||
|
||||
void start_data()
|
||||
{
|
||||
out_buffer = out_ptr = dbuffer;
|
||||
}
|
||||
|
||||
void end_file()
|
||||
{
|
||||
FILE *fp;
|
||||
int i, c;
|
||||
|
||||
buffer[I_FLAGOFF] &= (~INITED_MASK);
|
||||
switch(mode) {
|
||||
case FULL:
|
||||
case FORK:
|
||||
fp = fopen(f_info, "w");
|
||||
if(fp == NULL) {
|
||||
perror(f_info);
|
||||
exit(1);
|
||||
}
|
||||
(void)fwrite(buffer, 1, 128, fp);
|
||||
(void)fclose(fp);
|
||||
if(rsz != 0 || mode == FULL) {
|
||||
fp = fopen(f_rsrc, "w");
|
||||
if(fp == NULL) {
|
||||
perror(f_rsrc);
|
||||
exit(1);
|
||||
}
|
||||
(void)fwrite(rbuffer, 1, (int)rsz, fp);
|
||||
(void)fclose(fp);
|
||||
}
|
||||
if(dsz != 0 || mode == FULL) {
|
||||
fp = fopen(f_data, "w");
|
||||
if(fp == NULL) {
|
||||
perror(f_data);
|
||||
exit(1);
|
||||
}
|
||||
(void)fwrite(dbuffer, 1, (int)dsz, fp);
|
||||
(void)fclose(fp);
|
||||
}
|
||||
break;
|
||||
case RSRC:
|
||||
fp = fopen(f_rsrc, "w");
|
||||
if(fp == NULL) {
|
||||
perror(f_rsrc);
|
||||
exit(1);
|
||||
}
|
||||
(void)fwrite(rbuffer, 1, (int)rsz, fp);
|
||||
(void)fclose(fp);
|
||||
break;
|
||||
case DATA:
|
||||
fp = fopen(f_data, "w");
|
||||
if(fp == NULL) {
|
||||
perror(f_data);
|
||||
exit(1);
|
||||
}
|
||||
(void)fwrite(dbuffer, 1, (int)dsz, fp);
|
||||
(void)fclose(fp);
|
||||
break;
|
||||
case TEXT:
|
||||
fp = fopen(f_text, "w");
|
||||
if(fp == NULL) {
|
||||
perror(f_data);
|
||||
exit(1);
|
||||
}
|
||||
for(i = 0; i < dsz; i++) {
|
||||
c = dbuffer[i];
|
||||
if(c == '\012' || c == '\015') {
|
||||
dbuffer[i] = '\027' -c;
|
||||
}
|
||||
}
|
||||
(void)fwrite(dbuffer, 1, (int)dsz, fp);
|
||||
(void)fclose(fp);
|
||||
break;
|
||||
case UNIX:
|
||||
fp = fopen(f_unix, "w");
|
||||
if(fp == NULL) {
|
||||
perror(f_data);
|
||||
exit(1);
|
||||
}
|
||||
for(i = 0; i < dsz; i++) {
|
||||
c = dbuffer[i];
|
||||
if(c == '\012' || c == '\015') {
|
||||
dbuffer[i] = '\027' -c;
|
||||
}
|
||||
}
|
||||
(void)fwrite(dbuffer, 1, (int)dsz, fp);
|
||||
(void)fclose(fp);
|
||||
break;
|
||||
case MACB:
|
||||
fp = fopen(f_bin, "w");
|
||||
if(fp == NULL) {
|
||||
perror(f_bin);
|
||||
exit(1);
|
||||
}
|
||||
if(buffer[I_FLAGOFF + 1] & PROTCT_MASK) {
|
||||
buffer[I_LOCKOFF] = 1;
|
||||
}
|
||||
buffer[I_FLAGOFF + 1] = 0;
|
||||
buffer[I_LOCKOFF + 1] = 0;
|
||||
(void)fwrite(buffer, 1, (int)totsize, fp);
|
||||
(void)fclose(fp);
|
||||
break;
|
||||
case MACS:
|
||||
#ifdef SCAN
|
||||
case MACI:
|
||||
#endif /* SCAN */
|
||||
if(buffer[I_FLAGOFF + 1] & PROTCT_MASK) {
|
||||
buffer[I_LOCKOFF] = 1;
|
||||
}
|
||||
buffer[I_FLAGOFF + 1] = 0;
|
||||
buffer[I_LOCKOFF + 1] = 0;
|
||||
(void)fwrite(buffer, 1, (int)totsize, stdout);
|
||||
break;
|
||||
#ifdef AUFS
|
||||
case APSH:
|
||||
fp = fopen(f_info_aufs, "w");
|
||||
if(fp == NULL) {
|
||||
perror(f_info_aufs);
|
||||
exit(1);
|
||||
}
|
||||
wr_aufs_info(fp);
|
||||
(void) fclose(fp);
|
||||
fp = fopen(f_rsrc_aufs, "w");
|
||||
if(fp == NULL) {
|
||||
perror(f_rsrc_aufs);
|
||||
exit(1);
|
||||
}
|
||||
(void)fwrite(rbuffer, 1, (int)rsz, fp);
|
||||
(void)fclose(fp);
|
||||
fp = fopen(f_data, "w");
|
||||
if(fp == NULL) {
|
||||
perror(f_data);
|
||||
exit(1);
|
||||
}
|
||||
(void)fwrite(dbuffer, 1, (int)dsz, fp);
|
||||
(void)fclose(fp);
|
||||
break;
|
||||
#endif /* AUFS */
|
||||
#ifdef APPLEDOUBLE
|
||||
case APSH:
|
||||
fp = fopen(f_info_appledouble, "w");
|
||||
if(fp == NULL) {
|
||||
perror(f_info_appledouble);
|
||||
exit(1);
|
||||
}
|
||||
wr_appledouble_info(fp);
|
||||
(void)fwrite(rbuffer, 1, (int)rsz, fp);
|
||||
(void)fclose(fp);
|
||||
fp = fopen(f_data, "w");
|
||||
if(fp == NULL) {
|
||||
perror(f_data);
|
||||
exit(1);
|
||||
}
|
||||
(void)fwrite(dbuffer, 1, (int)dsz, fp);
|
||||
(void)fclose(fp);
|
||||
break;
|
||||
#endif /* APPLEDOUBLE */
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef SCAN
|
||||
void do_idf(name, kind)
|
||||
char *name;
|
||||
int kind;
|
||||
{
|
||||
int n;
|
||||
|
||||
if(mode != MACI) {
|
||||
return;
|
||||
}
|
||||
n = strlen(name);
|
||||
(void)bzero(buffer, INFOBYTES);
|
||||
buffer[I_NAMEOFF + 1] = kind;
|
||||
put4(buffer + I_DLENOFF, (unsigned long)n);
|
||||
(void)fwrite(buffer, 1, INFOBYTES, stdout);
|
||||
if(n != 0) {
|
||||
(void)fwrite(name, 1, n, stdout);
|
||||
n = (((n + 127) >> 7) << 7) - n;
|
||||
while(n-- > 0) {
|
||||
(void)fputc(0, stdout);
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif /* SCAN */
|
||||
|
||||
void do_mkdir(name, header)
|
||||
char *name, *header;
|
||||
{
|
||||
struct stat sbuf;
|
||||
FILE *fp;
|
||||
#ifdef NOMKDIR
|
||||
char command[21]; /* Systems without mkdir system call but more than 14
|
||||
char file names? Ridiculous! */
|
||||
int sysreturn;
|
||||
#endif /* MKDIR */
|
||||
#ifdef APPLESHARE
|
||||
char dirinfo[I_NAMELEN*3+INFOSZ+10];
|
||||
#endif /* APPLESHARE */
|
||||
|
||||
#ifndef SCAN
|
||||
if(mode == MACS) {
|
||||
#else /* SCAN */
|
||||
if(mode == MACS || mode == MACI) {
|
||||
#endif /* SCAN */
|
||||
header[I_NAMEOFF] |= 0x80;
|
||||
(void)fwrite(header, 1, INFOBYTES, stdout);
|
||||
header[I_NAMEOFF] &= 0x7f;
|
||||
return;
|
||||
}
|
||||
#ifdef APPLESHARE
|
||||
if(mode == APSH) {
|
||||
(void)bcopy(header, buffer, INFOBYTES);
|
||||
mk_share_name();
|
||||
} else {
|
||||
(void)strcpy(share_name, name);
|
||||
}
|
||||
#else /* APPLESHARE */
|
||||
(void)strcpy(share_name, name);
|
||||
#endif /* APPLESHARE */
|
||||
if(stat(share_name, &sbuf) == -1) { /* directory doesn't exist */
|
||||
#ifndef NOMKDIR
|
||||
if(mkdir(share_name, 0777) == -1) {
|
||||
(void)fprintf(stderr, "Can't create subdirectory %s\n", share_name);
|
||||
exit(1);
|
||||
}
|
||||
#else /* NOMKDIR */
|
||||
sprintf(command, "mkdir %s", share_name);
|
||||
if((sysreturn = system(command)) != 0) {
|
||||
(void)fprintf(stderr, "Can't create subdirectory %s\n", share_name);
|
||||
exit(sysreturn);
|
||||
}
|
||||
#endif /* NOMKDIR */
|
||||
} else { /* something exists with this name */
|
||||
if((sbuf.st_mode & S_IFMT) != S_IFDIR) {
|
||||
(void)fprintf(stderr, "Directory name %s already in use\n",
|
||||
share_name);
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
(void)chdir(share_name);
|
||||
#ifdef APPLESHARE
|
||||
#ifdef AUFS
|
||||
if(mode == APSH) {
|
||||
if(stat(rsrcdir, &sbuf) == -1) { /* directory doesn't exist */
|
||||
if(mkdir(rsrcdir, 0777) == -1) {
|
||||
(void)fprintf(stderr, "Can't create subdirectory %s\n",
|
||||
rsrcdir);
|
||||
exit(1);
|
||||
}
|
||||
} else {
|
||||
if((sbuf.st_mode & S_IFMT) != S_IFDIR) {
|
||||
(void)fprintf(stderr, "Directory name %s already in use\n",
|
||||
rsrcdir);
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
if(stat(infodir, &sbuf) == -1) { /* directory doesn't exist */
|
||||
if(mkdir(infodir, 0777) == -1) {
|
||||
(void)fprintf(stderr, "Can't create subdirectory %s\n",
|
||||
infodir);
|
||||
exit(1);
|
||||
}
|
||||
} else {
|
||||
if((sbuf.st_mode & S_IFMT) != S_IFDIR) {
|
||||
(void)fprintf(stderr, "Directory name %s already in use\n",
|
||||
infodir);
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
dirinfo[0] = 0;
|
||||
(void)strcat(dirinfo, "../");
|
||||
(void)strcat(dirinfo, infodir);
|
||||
(void)strcat(dirinfo, "/");
|
||||
(void)strcat(dirinfo, share_name);
|
||||
fp = fopen(dirinfo, "w");
|
||||
if(fp == NULL) {
|
||||
perror(dirinfo);
|
||||
exit(1);
|
||||
}
|
||||
wr_aufs_info(fp);
|
||||
(void)fclose(fp);
|
||||
} else {
|
||||
fp = fopen(f_folder, "w");
|
||||
if(fp == NULL) {
|
||||
perror(f_folder);
|
||||
exit(1);
|
||||
}
|
||||
header[I_NAMEOFF] |= 0x80;
|
||||
(void)fwrite(header, 1, INFOBYTES, fp);
|
||||
header[I_NAMEOFF] &= 0x7f;
|
||||
(void)fclose(fp);
|
||||
}
|
||||
#endif /* AUFS */
|
||||
#ifdef APPLEDOUBLE
|
||||
if(mode == APSH) {
|
||||
if(stat(infodir, &sbuf) == -1) { /* directory doesn't exist */
|
||||
if(mkdir(infodir, 0777) == -1) {
|
||||
(void)fprintf(stderr, "Can't create subdirectory %s\n",
|
||||
infodir);
|
||||
exit(1);
|
||||
}
|
||||
} else {
|
||||
if((sbuf.st_mode & S_IFMT) != S_IFDIR) {
|
||||
(void)fprintf(stderr, "Directory name %s already in use\n",
|
||||
infodir);
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
dirinfo[0] = 0;
|
||||
(void)strcat(dirinfo, infodir);
|
||||
(void)strcat(dirinfo, "/.Parent");
|
||||
fp = fopen(dirinfo, "w");
|
||||
if(fp == NULL) {
|
||||
perror(dirinfo);
|
||||
exit(1);
|
||||
}
|
||||
rsz = 0;
|
||||
wr_appledouble_info(fp);
|
||||
(void)fclose(fp);
|
||||
} else {
|
||||
fp = fopen(f_folder, "w");
|
||||
if(fp == NULL) {
|
||||
perror(f_folder);
|
||||
exit(1);
|
||||
}
|
||||
header[I_NAMEOFF] |= 0x80;
|
||||
(void)fwrite(header, 1, INFOBYTES, fp);
|
||||
header[I_NAMEOFF] &= 0x7f;
|
||||
(void)fclose(fp);
|
||||
}
|
||||
#endif /* APPLEDOUBLE */
|
||||
#else /* APPLESHARE */
|
||||
fp = fopen(f_folder, "w");
|
||||
if(fp == NULL) {
|
||||
perror(f_folder);
|
||||
exit(1);
|
||||
}
|
||||
header[I_NAMEOFF] |= 0x80;
|
||||
(void)fwrite(header, 1, INFOBYTES, fp);
|
||||
header[I_NAMEOFF] &= 0x7f;
|
||||
(void)fclose(fp);
|
||||
#endif /* APPLESHARE */
|
||||
}
|
||||
|
||||
void enddir()
|
||||
{
|
||||
char header[INFOBYTES];
|
||||
int i;
|
||||
|
||||
#ifndef SCAN
|
||||
if(mode == MACS) {
|
||||
#else /* SCAN */
|
||||
if(mode == MACS || mode == MACI) {
|
||||
#endif /* SCAN */
|
||||
for(i = 0; i < INFOBYTES; i++) {
|
||||
header[i] = 0;
|
||||
}
|
||||
header[I_NAMEOFF] = 0x80;
|
||||
(void)fwrite(header, 1, INFOBYTES, stdout);
|
||||
} else {
|
||||
(void)chdir("..");
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef APPLESHARE
|
||||
#ifdef AUFS
|
||||
static void check_aufs()
|
||||
{
|
||||
/* check for .resource/ and .finderinfo/ */
|
||||
struct stat stbuf;
|
||||
int error = 0;
|
||||
|
||||
if(stat(rsrcdir,&stbuf) < 0) {
|
||||
error ++;
|
||||
} else {
|
||||
if((stbuf.st_mode & S_IFMT) != S_IFDIR) {
|
||||
error ++;
|
||||
}
|
||||
}
|
||||
if(stat(infodir,&stbuf) < 0) {
|
||||
error ++;
|
||||
} else {
|
||||
if((stbuf.st_mode & S_IFMT) != S_IFDIR) {
|
||||
error++;
|
||||
}
|
||||
}
|
||||
if(error) {
|
||||
(void)fprintf(stderr, "Not in an Aufs folder.\n");
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
static void aufs_namings()
|
||||
{
|
||||
mk_share_name();
|
||||
(void)sprintf(f_info_aufs, "%s/%s", infodir, share_name);
|
||||
(void)sprintf(f_rsrc_aufs, "%s/%s", rsrcdir, share_name);
|
||||
(void)sprintf(f_data, "%s", share_name);
|
||||
}
|
||||
|
||||
static void wr_aufs_info(fp)
|
||||
FILE *fp;
|
||||
{
|
||||
FileInfo theinfo;
|
||||
int n;
|
||||
|
||||
bzero((char *) &theinfo, sizeof theinfo);
|
||||
theinfo.fi_magic1 = FI_MAGIC1;
|
||||
theinfo.fi_version = FI_VERSION;
|
||||
theinfo.fi_magic = FI_MAGIC;
|
||||
theinfo.fi_bitmap = FI_BM_MACINTOSHFILENAME;
|
||||
|
||||
/* AUFS stores Unix times. */
|
||||
#ifdef AUFSPLUS
|
||||
theinfo.fi_datemagic = FI_MAGIC;
|
||||
theinfo.fi_datevalid = FI_CDATE | FI_MDATE;
|
||||
put4(theinfo.fi_ctime, get4(buffer + I_CTIMOFF) - TIMEDIFF);
|
||||
put4(theinfo.fi_mtime, get4(buffer + I_MTIMOFF) - TIMEDIFF);
|
||||
put4(theinfo.fi_utime, (unsigned long)time((time_t *)0));
|
||||
#endif /* AUFSPLUS */
|
||||
bcopy(buffer + I_TYPEOFF, theinfo.fi_fndr, 4);
|
||||
bcopy(buffer + I_AUTHOFF, theinfo.fi_fndr + 4, 4);
|
||||
bcopy(buffer + I_FLAGOFF, theinfo.fi_fndr + 8, 2);
|
||||
if((n = buffer[I_NAMEOFF] & 0xff) > F_NAMELEN) {
|
||||
n = F_NAMELEN;
|
||||
}
|
||||
(void)strncpy((char *)theinfo.fi_macfilename, buffer + I_NAMEOFF + 1,n);
|
||||
/* theinfo.fi_macfilename[n] = '\0'; */
|
||||
(void)strcpy((char *)theinfo.fi_comnt,
|
||||
"Converted by Unix utility to Aufs format");
|
||||
theinfo.fi_comln = strlen((char *)theinfo.fi_comnt);
|
||||
(void)fwrite((char *) &theinfo, 1, sizeof theinfo, fp);
|
||||
}
|
||||
#endif /* AUFS */
|
||||
|
||||
#ifdef APPLEDOUBLE
|
||||
static void check_appledouble()
|
||||
{
|
||||
/* check for .AppleDouble/ */
|
||||
struct stat stbuf;
|
||||
int error = 0;
|
||||
|
||||
if(stat(infodir,&stbuf) < 0) {
|
||||
error ++;
|
||||
} else {
|
||||
if((stbuf.st_mode & S_IFMT) != S_IFDIR) {
|
||||
error++;
|
||||
}
|
||||
}
|
||||
if(error) {
|
||||
(void)fprintf(stderr, "Not in an AppleDouble folder.\n");
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
static void appledouble_namings()
|
||||
{
|
||||
mk_share_name();
|
||||
(void)sprintf(f_info_appledouble, "%s/%s", infodir, share_name);
|
||||
(void)sprintf(f_data, "%s", share_name);
|
||||
}
|
||||
|
||||
static void wr_appledouble_info(fp)
|
||||
FILE *fp;
|
||||
{
|
||||
FileInfo theinfo;
|
||||
int n;
|
||||
|
||||
bzero((char *) &theinfo, sizeof theinfo);
|
||||
put4(theinfo.fi_magic, (unsigned long)FI_MAGIC);
|
||||
put2(theinfo.fi_version, (unsigned long)FI_VERSION);
|
||||
put4(theinfo.fi_fill5, (unsigned long)FI_FILL5);
|
||||
put4(theinfo.fi_fill6, (unsigned long)FI_FILL6);
|
||||
put4(theinfo.fi_hlen, (unsigned long)FI_HLEN);
|
||||
put4(theinfo.fi_fill7, (unsigned long)FI_FILL7);
|
||||
put4(theinfo.fi_namptr, (unsigned long)FI_NAMPTR);
|
||||
put4(theinfo.fi_fill9, (unsigned long)FI_FILL9);
|
||||
put4(theinfo.fi_commptr, (unsigned long)FI_COMMPTR);
|
||||
put4(theinfo.fi_fill12, (unsigned long)FI_FILL12);
|
||||
put4(theinfo.fi_timeptr, (unsigned long)FI_TIMEPTR);
|
||||
put4(theinfo.fi_timesize, (unsigned long)FI_TIMESIZE);
|
||||
put4(theinfo.fi_fill15, (unsigned long)FI_FILL15);
|
||||
put4(theinfo.fi_infoptr, (unsigned long)FI_INFOPTR);
|
||||
put4(theinfo.fi_infosize, (unsigned long)FI_INFOSIZE);
|
||||
|
||||
bcopy(buffer + I_TYPEOFF, theinfo.fi_type, 4);
|
||||
bcopy(buffer + I_AUTHOFF, theinfo.fi_auth, 4);
|
||||
bcopy(buffer + I_FLAGOFF, theinfo.fi_finfo, 2);
|
||||
/* AppleDouble stores Unix times. */
|
||||
put4(theinfo.fi_ctime, get4(buffer + I_CTIMOFF) - TIMEDIFF);
|
||||
put4(theinfo.fi_mtime, get4(buffer + I_MTIMOFF) - TIMEDIFF);
|
||||
if((n = buffer[I_NAMEOFF] & 0xff) > F_NAMELEN) {
|
||||
n = F_NAMELEN;
|
||||
}
|
||||
put4(theinfo.fi_namlen, (unsigned long)n);
|
||||
(void)strncpy((char *)theinfo.fi_name, buffer + I_NAMEOFF + 1,n);
|
||||
/* theinfo.fi_macfilename[n] = '\0'; */
|
||||
(void)strcpy((char *)theinfo.fi_comment,
|
||||
"Converted by Unix utility to AppleDouble format");
|
||||
put4(theinfo.fi_commsize, (unsigned long)strlen(theinfo.fi_comment));
|
||||
put4(theinfo.fi_rsrc, (unsigned long)rsz);
|
||||
/* Still TODO */
|
||||
/* char fi_ctime[4]; /* Creation time (Unix time) */
|
||||
/* char fi_mtime[4]; /* Modification time (Unix time) */
|
||||
(void)fwrite((char *) &theinfo, 1, sizeof theinfo, fp);
|
||||
}
|
||||
#endif /* APPLEDOUBLE */
|
||||
|
||||
static void mk_share_name()
|
||||
{
|
||||
int ch;
|
||||
char *mp, *up;
|
||||
|
||||
mp = buffer + 2;
|
||||
up = &(share_name[0]);
|
||||
while(ch = *mp++) {
|
||||
if(isascii(ch) && ! iscntrl(ch) && isprint(ch) && ch != '/') {
|
||||
*up++ = ch;
|
||||
} else {
|
||||
*up++ = ':';
|
||||
*up++ = hex[(ch >> 4) & 0xf];
|
||||
*up++ = hex[ch & 0xf];
|
||||
}
|
||||
}
|
||||
*up = 0;
|
||||
}
|
||||
#endif /* APPLESHARE */
|
||||
|
||||
int wrfileopt(c)
|
||||
char c;
|
||||
{
|
||||
switch(c) {
|
||||
case 'b':
|
||||
mode = MACB;
|
||||
break;
|
||||
case 'r':
|
||||
if(mode_restricted) {
|
||||
return 0;
|
||||
}
|
||||
mode = RSRC;
|
||||
break;
|
||||
case 'd':
|
||||
if(mode_restricted) {
|
||||
return 0;
|
||||
}
|
||||
mode = DATA;
|
||||
break;
|
||||
case 'u':
|
||||
if(mode_restricted) {
|
||||
return 0;
|
||||
}
|
||||
mode = TEXT;
|
||||
break;
|
||||
case 'U':
|
||||
if(mode_restricted) {
|
||||
return 0;
|
||||
}
|
||||
mode = UNIX;
|
||||
break;
|
||||
case 'f':
|
||||
mode = FORK;
|
||||
break;
|
||||
case '3':
|
||||
mode = FULL;
|
||||
break;
|
||||
case 's':
|
||||
if(mode_s_restricted) {
|
||||
return 0;
|
||||
}
|
||||
mode = MACS;
|
||||
break;
|
||||
#ifdef SCAN
|
||||
case 'S':
|
||||
if(mode_s_restricted) {
|
||||
return 0;
|
||||
}
|
||||
mode = MACI;
|
||||
break;
|
||||
#endif /* SCAN */
|
||||
case 'a':
|
||||
#ifdef APPLESHARE
|
||||
#ifdef AUFS
|
||||
check_aufs();
|
||||
mode = APSH;
|
||||
break;
|
||||
#endif /* AUFS */
|
||||
#ifdef APPLEDOUBLE
|
||||
check_appledouble();
|
||||
mode = APSH;
|
||||
break;
|
||||
#endif /* APPLEDOUBLE */
|
||||
#else /* APPLESHARE */
|
||||
(void)fprintf(stderr, "Sorry, Apple-Unix sharing is not supported.\n");
|
||||
(void)fprintf(stderr, "Recompile or omit -a option.\n");
|
||||
exit(1);
|
||||
#endif /* APPLESHARE */
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
void give_wrfileopt()
|
||||
{
|
||||
(void)fprintf(stderr, "File output options:\n");
|
||||
(void)fprintf(stderr, "-b:\tMacBinary (default)\n");
|
||||
if(!mode_s_restricted) {
|
||||
(void)fprintf(stderr, "-s:\tMacBinary stream to standard output\n");
|
||||
#ifdef SCAN
|
||||
(void)fprintf(stderr,
|
||||
"-S:\tas -s but with indication of orignal Unix filename\n");
|
||||
#endif /* SCAN */
|
||||
}
|
||||
(void)fprintf(stderr, "-f:\tthree fork mode, skipping empty forks\n");
|
||||
(void)fprintf(stderr, "-3:\tthe same, writing also empty forks\n");
|
||||
if(!mode_restricted) {
|
||||
(void)fprintf(stderr, "-r:\tresource forks only\n");
|
||||
(void)fprintf(stderr, "-d:\tdata forks only\n");
|
||||
(void)fprintf(stderr,
|
||||
"-u:\tdata forks only with Mac -> Unix text file translation\n");
|
||||
(void)fprintf(stderr,
|
||||
"-U:\tas -u, but filename will not have an extension\n");
|
||||
}
|
||||
#ifdef APPLESHARE
|
||||
#ifdef AUFS
|
||||
(void)fprintf(stderr, "-a:\tAUFS format\n");
|
||||
#endif /* AUFS */
|
||||
#ifdef APPLEDOUBLE
|
||||
(void)fprintf(stderr, "-a:\tAppleDouble format\n");
|
||||
#endif /* APPLEDOUBLE */
|
||||
#else /* APPLESHARE */
|
||||
(void)fprintf(stderr, "-a:\tnot supported, needs recompilation\n");
|
||||
#endif /* APPLESHARE */
|
||||
}
|
||||
|
||||
void set_wrfileopt(restricted)
|
||||
{
|
||||
mode_restricted = restricted;
|
||||
}
|
||||
|
||||
void set_s_wrfileopt(restricted)
|
||||
{
|
||||
mode_s_restricted = restricted;
|
||||
}
|
||||
|
||||
char *get_wrfileopt()
|
||||
{
|
||||
static char options[20];
|
||||
|
||||
(void)strcpy(options, "b");
|
||||
if(!mode_s_restricted) {
|
||||
(void)strcat(options, "s");
|
||||
#ifdef SCAN
|
||||
(void)strcat(options, "S");
|
||||
#endif /* SCAN */
|
||||
}
|
||||
(void)strcat(options, "f3");
|
||||
if(!mode_restricted) {
|
||||
(void)strcat(options, "rduU");
|
||||
}
|
||||
(void)strcat(options, "a");
|
||||
return options;
|
||||
}
|
||||
|
||||
char *get_mina()
|
||||
{
|
||||
#ifdef APPLESHARE
|
||||
#ifdef AUFS
|
||||
return ", AUFS supported";
|
||||
#endif /* AUFS */
|
||||
#ifdef APPLEDOUBLE
|
||||
return ", AppleDouble supported";
|
||||
#endif /* APPLEDOUBLE */
|
||||
#else /* APPLESHARE */
|
||||
return ", no Apple-Unix sharing supported";
|
||||
#endif /* APPLESHARE */
|
||||
}
|
||||
|
14
fileio/wrfile.h
Executable file
14
fileio/wrfile.h
Executable file
@ -0,0 +1,14 @@
|
||||
extern char *out_buffer, *out_ptr;
|
||||
|
||||
extern void define_name();
|
||||
extern void start_info();
|
||||
extern void start_rsrc();
|
||||
extern void start_data();
|
||||
extern void end_file();
|
||||
#ifdef SCAN
|
||||
extern void do_idf();
|
||||
#endif /* SCAN */
|
||||
extern void do_mkdir();
|
||||
extern void enddir();
|
||||
extern char *get_mina();
|
||||
|
BIN
fileio/wrfile.o
Normal file
BIN
fileio/wrfile.o
Normal file
Binary file not shown.
6
fileio/wrfileopt.h
Executable file
6
fileio/wrfileopt.h
Executable file
@ -0,0 +1,6 @@
|
||||
extern int wrfileopt();
|
||||
extern void give_wrfileopt();
|
||||
extern void set_wrfileopt();
|
||||
extern void set_s_wrfileopt();
|
||||
extern char *get_wrfileopt();
|
||||
|
76
hexbin/buffer.c
Executable file
76
hexbin/buffer.c
Executable file
@ -0,0 +1,76 @@
|
||||
#include "globals.h"
|
||||
#include "../util/util.h"
|
||||
#include "buffer.h"
|
||||
#include "../fileio/wrfile.h"
|
||||
|
||||
extern char *malloc();
|
||||
extern char *realloc();
|
||||
extern void exit();
|
||||
|
||||
char *data_fork, *rsrc_fork;
|
||||
int data_size, rsrc_size;
|
||||
static int max_data_size, max_rsrc_size;
|
||||
static int do_data;
|
||||
|
||||
void put_byte(c)
|
||||
char c;
|
||||
{
|
||||
if(do_data) {
|
||||
if(data_size >= max_data_size) {
|
||||
if(max_data_size == 0) {
|
||||
data_fork = malloc(1024);
|
||||
} else {
|
||||
data_fork = realloc(data_fork, (unsigned)max_data_size + 1024);
|
||||
}
|
||||
max_data_size += 1024;
|
||||
if(data_fork == NULL) {
|
||||
(void)fprintf(stderr, "Insufficient memory.\n");
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
data_fork[data_size++] = c;
|
||||
} else {
|
||||
if(rsrc_size >= max_rsrc_size) {
|
||||
if(max_rsrc_size == 0) {
|
||||
rsrc_fork = malloc(1024);
|
||||
} else {
|
||||
rsrc_fork = realloc(rsrc_fork, (unsigned)max_rsrc_size + 1024);
|
||||
}
|
||||
max_rsrc_size += 1024;
|
||||
if(rsrc_fork == NULL) {
|
||||
(void)fprintf(stderr, "Insufficient memory.\n");
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
rsrc_fork[rsrc_size++] = c;
|
||||
}
|
||||
}
|
||||
|
||||
void set_put(data)
|
||||
int data;
|
||||
{
|
||||
do_data = data;
|
||||
if(do_data) {
|
||||
data_size = 0;
|
||||
} else {
|
||||
rsrc_size = 0;
|
||||
}
|
||||
}
|
||||
|
||||
void end_put()
|
||||
{
|
||||
if(info_only) {
|
||||
return;
|
||||
}
|
||||
start_info(info, (unsigned long)rsrc_size, (unsigned long)data_size);
|
||||
if(data_size != 0) {
|
||||
start_data();
|
||||
copy(out_ptr, data_fork, data_size);
|
||||
}
|
||||
if(rsrc_size != 0) {
|
||||
start_rsrc();
|
||||
copy(out_ptr, rsrc_fork, rsrc_size);
|
||||
}
|
||||
end_file();
|
||||
}
|
||||
|
6
hexbin/buffer.h
Executable file
6
hexbin/buffer.h
Executable file
@ -0,0 +1,6 @@
|
||||
extern char *data_fork, *rsrc_fork;
|
||||
extern int data_size, rsrc_size;
|
||||
extern void put_byte();
|
||||
extern void set_put();
|
||||
extern void end_put();
|
||||
|
44
hexbin/crc.c
Executable file
44
hexbin/crc.c
Executable file
@ -0,0 +1,44 @@
|
||||
/* crc.c; do crc calculation. */
|
||||
|
||||
#include <stdio.h>
|
||||
#include "hexbin.h"
|
||||
#include "crc.h"
|
||||
#include "../util/masks.h"
|
||||
#include "globals.h"
|
||||
|
||||
extern void exit();
|
||||
|
||||
unsigned long crc;
|
||||
|
||||
#ifdef HQX
|
||||
void comp_q_crc(c)
|
||||
register unsigned int c;
|
||||
{
|
||||
unsigned char cc = c;
|
||||
|
||||
crc = binhex_updcrc(crc, &cc, 1);
|
||||
}
|
||||
|
||||
void comp_q_crc_n(s, e)
|
||||
register unsigned char *s, *e;
|
||||
{
|
||||
crc = binhex_updcrc(crc, s, e - s);
|
||||
}
|
||||
#endif /* HQX */
|
||||
|
||||
void verify_crc(calc_crc, file_crc)
|
||||
unsigned long calc_crc, file_crc;
|
||||
{
|
||||
calc_crc &= WORDMASK;
|
||||
file_crc &= WORDMASK;
|
||||
|
||||
if(calc_crc != file_crc) {
|
||||
(void)fprintf(stderr, "CRC mismatch: got 0x%04lx, need 0x%04lx\n",
|
||||
file_crc, calc_crc);
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: CRC error");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
10
hexbin/crc.h
Executable file
10
hexbin/crc.h
Executable file
@ -0,0 +1,10 @@
|
||||
#define INITCRC binhex_crcinit
|
||||
|
||||
extern unsigned long crc;
|
||||
extern unsigned long binhex_crcinit;
|
||||
extern unsigned long binhex_updcrc();
|
||||
|
||||
extern void comp_q_crc();
|
||||
extern void comp_q_crc_n();
|
||||
extern void verify_crc();
|
||||
|
134
hexbin/dl.c
Executable file
134
hexbin/dl.c
Executable file
@ -0,0 +1,134 @@
|
||||
#include "hexbin.h"
|
||||
#ifdef DL
|
||||
#include "globals.h"
|
||||
#include "crc.h"
|
||||
#include "readline.h"
|
||||
#include "../fileio/machdr.h"
|
||||
#include "../fileio/wrfile.h"
|
||||
#include "../util/util.h"
|
||||
#include "buffer.h"
|
||||
#include "printhdr.h"
|
||||
|
||||
extern void exit();
|
||||
|
||||
static long dl_fork();
|
||||
static int nchar();
|
||||
static int nextc();
|
||||
|
||||
static char *icp = &line[0];
|
||||
|
||||
/* oldest format -- process .dl files */
|
||||
void dl(macname, filename)
|
||||
char *macname, *filename;
|
||||
{
|
||||
int n;
|
||||
|
||||
if(listmode) {
|
||||
(void)fprintf(stderr, "This file is in \"dl\" format.\n");
|
||||
}
|
||||
for(n = 0; n < INFOBYTES; n++) {
|
||||
info[n] = 0;
|
||||
}
|
||||
/* set up for Mac name */
|
||||
if(macname[0] == '\0') {
|
||||
/* strip directories */
|
||||
macname = search_last(filename, '/');
|
||||
if(macname == NULL) {
|
||||
macname = filename;
|
||||
} else {
|
||||
macname++;
|
||||
}
|
||||
/* strip extension */
|
||||
n = strlen(macname);
|
||||
if(n > 3) {
|
||||
n -= 3;
|
||||
if(!strncmp(macname + n, ".dl", 3)) {
|
||||
macname[n] = '\0';
|
||||
}
|
||||
}
|
||||
}
|
||||
n = strlen(macname);
|
||||
if(n > F_NAMELEN) {
|
||||
n = F_NAMELEN;
|
||||
}
|
||||
(void)strncpy(mh.m_name, macname, n);
|
||||
(void)strncpy(mh.m_type, "APPL", 4);
|
||||
(void)strncpy(mh.m_author, "????", 4);
|
||||
mh.m_name[n] = '\0';
|
||||
transname(mh.m_name, trname, n);
|
||||
define_name(trname);
|
||||
print_header0(0);
|
||||
print_header1(0, 0);
|
||||
set_put(1);
|
||||
mh.m_datalen = 0;
|
||||
set_put(0);
|
||||
mh.m_rsrclen = dl_fork();
|
||||
info[I_NAMEOFF] = n;
|
||||
(void)strncpy(info + I_NAMEOFF + 1, mh.m_name, n);
|
||||
(void)strncpy(info + I_TYPEOFF, mh.m_type, 4);
|
||||
(void)strncpy(info + I_AUTHOFF, mh.m_author, 4);
|
||||
put4(info + I_DLENOFF, (unsigned long)mh.m_datalen);
|
||||
put4(info + I_RLENOFF, (unsigned long)mh.m_rsrclen);
|
||||
put4(info + I_CTIMOFF, (unsigned long)mh.m_createtime);
|
||||
put4(info + I_MTIMOFF, (unsigned long)mh.m_modifytime);
|
||||
print_header2(0);
|
||||
end_put();
|
||||
}
|
||||
|
||||
static long dl_fork()
|
||||
{
|
||||
register unsigned long i, v, c;
|
||||
register unsigned long n, bytes;
|
||||
|
||||
n = 0;
|
||||
bytes = 0;
|
||||
v = 0;
|
||||
crc = 0;
|
||||
while((i = nchar()) != '|') {
|
||||
if(i < '@' || i > 'O') {
|
||||
continue;
|
||||
}
|
||||
v = (v << 4) | (i & 0xF);
|
||||
if((++n & 1) == 0) {
|
||||
put_byte((char)v);
|
||||
crc += v;
|
||||
v = 0;
|
||||
bytes++;
|
||||
}
|
||||
}
|
||||
c = 0;
|
||||
for(i = 0 ; i < 8 ; i++) {
|
||||
c = (c << 4) | (nchar() & 0xF);
|
||||
}
|
||||
verify_crc(bytes + crc, c);
|
||||
return bytes;
|
||||
}
|
||||
|
||||
static int nchar()
|
||||
{
|
||||
int i;
|
||||
|
||||
if((i = nextc()) == EOF) {
|
||||
(void)fprintf(stderr, "Premature EOF\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: Premature EOF");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
return i & 0177;
|
||||
}
|
||||
|
||||
static int nextc()
|
||||
{
|
||||
while(*icp == 0) {
|
||||
if(readline() == 0) {
|
||||
return EOF;
|
||||
}
|
||||
icp = &line[0];
|
||||
}
|
||||
return *icp++;
|
||||
}
|
||||
#else /* DL */
|
||||
int dl; /* keep lint and some compilers happy */
|
||||
#endif /* DL */
|
||||
|
27
hexbin/globals.c
Executable file
27
hexbin/globals.c
Executable file
@ -0,0 +1,27 @@
|
||||
#include "globals.h"
|
||||
#include "../fileio/machdr.h"
|
||||
#include "../fileio/wrfile.h"
|
||||
#include "../fileio/kind.h"
|
||||
|
||||
struct macheader mh;
|
||||
|
||||
char info[INFOBYTES];
|
||||
char trname[64];
|
||||
|
||||
int listmode;
|
||||
int info_only;
|
||||
int verbose;
|
||||
int uneven_lines;
|
||||
int to_read;
|
||||
int was_macbin;
|
||||
|
||||
FILE *ifp;
|
||||
|
||||
#ifdef SCAN
|
||||
void do_error(string)
|
||||
char *string;
|
||||
{
|
||||
do_idf(string, ERROR);
|
||||
}
|
||||
#endif /* SCAN */
|
||||
|
39
hexbin/globals.h
Executable file
39
hexbin/globals.h
Executable file
@ -0,0 +1,39 @@
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#ifdef BSD
|
||||
extern char *rindex();
|
||||
#define search_last rindex
|
||||
#else /* BSD */
|
||||
extern char *strrchr();
|
||||
#define search_last strrchr
|
||||
#endif /* BSD */
|
||||
|
||||
extern void transname();
|
||||
|
||||
extern char info[];
|
||||
extern char trname[];
|
||||
|
||||
typedef struct macheader {
|
||||
char m_name[128];
|
||||
char m_type[4];
|
||||
char m_author[4];
|
||||
short m_flags;
|
||||
long m_datalen;
|
||||
long m_rsrclen;
|
||||
long m_createtime;
|
||||
long m_modifytime;
|
||||
};
|
||||
|
||||
extern struct macheader mh;
|
||||
|
||||
extern int listmode;
|
||||
extern int verbose;
|
||||
extern int info_only;
|
||||
extern int uneven_lines;
|
||||
extern int to_read;
|
||||
extern int was_macbin;
|
||||
|
||||
extern FILE *ifp;
|
||||
|
||||
extern void do_error();
|
||||
|
256
hexbin/hecx.c
Executable file
256
hexbin/hecx.c
Executable file
@ -0,0 +1,256 @@
|
||||
#include "hexbin.h"
|
||||
#ifdef HECX
|
||||
#include "globals.h"
|
||||
#include "crc.h"
|
||||
#include "readline.h"
|
||||
#include "../util/masks.h"
|
||||
#include "../util/util.h"
|
||||
#include "../fileio/machdr.h"
|
||||
#include "../fileio/wrfile.h"
|
||||
#include "buffer.h"
|
||||
#include "printhdr.h"
|
||||
|
||||
extern void exit();
|
||||
|
||||
static void do_o_forks();
|
||||
static long make_file();
|
||||
static void comp_c_crc();
|
||||
static void comp_e_crc();
|
||||
static int comp_to_bin();
|
||||
static int hex_to_bin();
|
||||
static int hexit();
|
||||
|
||||
static int compressed;
|
||||
|
||||
/* old format -- process .hex and .hcx files */
|
||||
void hecx(macname, filename)
|
||||
char *macname, *filename;
|
||||
{
|
||||
int n;
|
||||
|
||||
for(n = 0; n < INFOBYTES; n++) {
|
||||
info[n] = 0;
|
||||
}
|
||||
compressed = 0;
|
||||
/* set up name for output files */
|
||||
if(macname[0] == '\0') {
|
||||
/* strip directories */
|
||||
macname = search_last(filename, '/');
|
||||
if(macname == NULL) {
|
||||
macname = filename;
|
||||
} else {
|
||||
macname++;
|
||||
}
|
||||
|
||||
/* strip extension */
|
||||
n = strlen(macname);
|
||||
if(n > 4) {
|
||||
n -= 4;
|
||||
if(!strncmp(macname + n, ".hex", 4) ||
|
||||
!strncmp(macname + n, ".hcx", 4)) {
|
||||
macname[n] = '\0';
|
||||
}
|
||||
}
|
||||
}
|
||||
n = strlen(macname);
|
||||
if(n > F_NAMELEN) {
|
||||
n = F_NAMELEN;
|
||||
}
|
||||
(void)strncpy(mh.m_name, macname, n);
|
||||
mh.m_name[n] = '\0';
|
||||
|
||||
/* "#TYPEAUTH$flag" line already read */
|
||||
n = strlen(line);
|
||||
if(n >= 6 && line[0] == '#' && line[n-5] == '$') {
|
||||
if(n >= 10) {
|
||||
(void)strncpy(mh.m_type, &line[1], 4);
|
||||
}
|
||||
if(n >= 14) {
|
||||
(void)strncpy(mh.m_author, &line[5], 4);
|
||||
}
|
||||
(void)sscanf(&line[n-4], "%4hx", &mh.m_flags);
|
||||
}
|
||||
transname(mh.m_name, trname, n);
|
||||
define_name(trname);
|
||||
do_o_forks();
|
||||
if(listmode) {
|
||||
if(!compressed) {
|
||||
(void)fprintf(stderr, "This file is in \"hex\" format.\n");
|
||||
} else {
|
||||
(void)fprintf(stderr, "This file is in \"hcx\" format.\n");
|
||||
}
|
||||
}
|
||||
print_header0(0);
|
||||
print_header1(0, 0);
|
||||
info[I_NAMEOFF] = n;
|
||||
(void)strncpy(info + I_NAMEOFF + 1, mh.m_name, n);
|
||||
(void)strncpy(info + I_TYPEOFF, mh.m_type, 4);
|
||||
(void)strncpy(info + I_AUTHOFF, mh.m_author, 4);
|
||||
put2(info + I_FLAGOFF, (unsigned long)mh.m_flags);
|
||||
put4(info + I_DLENOFF, (unsigned long)mh.m_datalen);
|
||||
put4(info + I_RLENOFF, (unsigned long)mh.m_rsrclen);
|
||||
put4(info + I_CTIMOFF, (unsigned long)mh.m_createtime);
|
||||
put4(info + I_MTIMOFF, (unsigned long)mh.m_modifytime);
|
||||
print_header2(0);
|
||||
end_put();
|
||||
}
|
||||
|
||||
static void do_o_forks()
|
||||
{
|
||||
int forks = 0, found_crc = 0;
|
||||
unsigned long calc_crc, file_crc;
|
||||
|
||||
crc = 0; /* calculate a crc for both forks */
|
||||
|
||||
set_put(0);
|
||||
set_put(1);
|
||||
while(!found_crc && readline()) {
|
||||
if(line[0] == 0) {
|
||||
continue;
|
||||
}
|
||||
if(forks == 0 && strncmp(line, "***COMPRESSED", 13) == 0) {
|
||||
compressed++;
|
||||
continue;
|
||||
}
|
||||
if(strncmp(line, "***DATA", 7) == 0) {
|
||||
set_put(1);
|
||||
mh.m_datalen = make_file(compressed);
|
||||
forks++;
|
||||
continue;
|
||||
}
|
||||
if(strncmp(line, "***RESOURCE", 11) == 0) {
|
||||
set_put(0);
|
||||
mh.m_rsrclen = make_file(compressed);
|
||||
forks++;
|
||||
continue;
|
||||
}
|
||||
if(compressed && strncmp(line, "***CRC:", 7) == 0) {
|
||||
found_crc++;
|
||||
calc_crc = crc;
|
||||
(void)sscanf(&line[7], "%lx", &file_crc);
|
||||
break;
|
||||
}
|
||||
if(!compressed && strncmp(line, "***CHECKSUM:", 12) == 0) {
|
||||
found_crc++;
|
||||
calc_crc = crc & BYTEMASK;
|
||||
(void)sscanf(&line[12], "%lx", &file_crc);
|
||||
file_crc &= BYTEMASK;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if(found_crc) {
|
||||
verify_crc(calc_crc, file_crc);
|
||||
} else {
|
||||
(void)fprintf(stderr, "missing CRC\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: missing CRC");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
static long make_file(compressed)
|
||||
int compressed;
|
||||
{
|
||||
register long nbytes = 0L;
|
||||
|
||||
while(readline()) {
|
||||
if(line[0] == 0) {
|
||||
continue;
|
||||
}
|
||||
if(strncmp(line, "***END", 6) == 0) {
|
||||
break;
|
||||
}
|
||||
if(compressed) {
|
||||
nbytes += comp_to_bin();
|
||||
} else {
|
||||
nbytes += hex_to_bin();
|
||||
}
|
||||
}
|
||||
return nbytes;
|
||||
}
|
||||
|
||||
static void comp_c_crc(c)
|
||||
unsigned char c;
|
||||
{
|
||||
crc = (crc + c) & WORDMASK;
|
||||
crc = ((crc << 3) & WORDMASK) | (crc >> 13);
|
||||
}
|
||||
|
||||
static void comp_e_crc(c)
|
||||
unsigned char c;
|
||||
{
|
||||
crc += c;
|
||||
}
|
||||
|
||||
#define SIXB(c) (((c)-0x20) & 0x3f)
|
||||
|
||||
static int comp_to_bin()
|
||||
{
|
||||
char obuf[BUFSIZ];
|
||||
register char *ip = line;
|
||||
register char *op = obuf;
|
||||
register int n, outcount;
|
||||
int numread, incount;
|
||||
|
||||
numread = strlen(line);
|
||||
outcount = (SIXB(ip[0]) << 2) | (SIXB(ip[1]) >> 4);
|
||||
incount = ((outcount / 3) + 1) * 4;
|
||||
for(n = numread; n < incount; n++) { /* restore lost spaces */
|
||||
line[n] = ' ';
|
||||
}
|
||||
|
||||
n = 0;
|
||||
while(n <= outcount) {
|
||||
*op++ = SIXB(ip[0]) << 2 | SIXB(ip[1]) >> 4;
|
||||
*op++ = SIXB(ip[1]) << 4 | SIXB(ip[2]) >> 2;
|
||||
*op++ = SIXB(ip[2]) << 6 | SIXB(ip[3]);
|
||||
ip += 4;
|
||||
n += 3;
|
||||
}
|
||||
|
||||
for(n = 1; n <= outcount; n++) {
|
||||
comp_c_crc((unsigned)obuf[n]);
|
||||
put_byte(obuf[n]);
|
||||
}
|
||||
return outcount;
|
||||
}
|
||||
|
||||
static int hex_to_bin()
|
||||
{
|
||||
register char *ip = line;
|
||||
register int n, outcount;
|
||||
int c;
|
||||
|
||||
n = strlen(line);
|
||||
outcount = n / 2;
|
||||
for(n = 0; n < outcount; n++) {
|
||||
c = hexit((int)*ip++);
|
||||
comp_e_crc((unsigned)(c = (c << 4) | hexit((int)*ip++)));
|
||||
put_byte((char)c);
|
||||
}
|
||||
return outcount;
|
||||
}
|
||||
|
||||
static int hexit(c)
|
||||
int c;
|
||||
{
|
||||
if('0' <= c && c <= '9') {
|
||||
return c - '0';
|
||||
}
|
||||
if('A' <= c && c <= 'F') {
|
||||
return c - 'A' + 10;
|
||||
}
|
||||
|
||||
(void)fprintf(stderr, "illegal hex digit: %c", c);
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: illegal hex digit");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
/* NOTREACHED */
|
||||
}
|
||||
#else /* HECX */
|
||||
int hecx; /* keep lint and some compilers happy */
|
||||
#endif /* HECX */
|
||||
|
362
hexbin/hexbin.c
Executable file
362
hexbin/hexbin.c
Executable file
@ -0,0 +1,362 @@
|
||||
#ifdef TYPES_H
|
||||
#include <sys/types.h>
|
||||
#endif /* TYPES_H */
|
||||
#include <sys/stat.h>
|
||||
#include "globals.h"
|
||||
#include "crc.h"
|
||||
#include "readline.h"
|
||||
#include "../util/masks.h"
|
||||
#include "../util/util.h"
|
||||
#include "../util/patchlevel.h"
|
||||
#include "../fileio/wrfile.h"
|
||||
#include "../fileio/wrfileopt.h"
|
||||
#include "../fileio/machdr.h"
|
||||
#include "../fileio/kind.h"
|
||||
#include "../util/curtime.h"
|
||||
#include "hexbin.h"
|
||||
|
||||
#define LOCALOPT "ilvcn:qVH"
|
||||
|
||||
extern void exit();
|
||||
extern void backtrans();
|
||||
#ifdef DL
|
||||
extern void dl();
|
||||
#endif /* DL */
|
||||
#ifdef HECX
|
||||
extern void hecx();
|
||||
#endif /* HECX */
|
||||
#ifdef HQX
|
||||
extern void hqx();
|
||||
#endif /* HQX */
|
||||
#ifdef MU
|
||||
extern void mu();
|
||||
#endif /* MU */
|
||||
|
||||
static void usage();
|
||||
static void do_files();
|
||||
static int find_header();
|
||||
|
||||
static char options[128];
|
||||
|
||||
int main(argc, argv)
|
||||
int argc;
|
||||
char **argv;
|
||||
{
|
||||
char *filename;
|
||||
char macname[32];
|
||||
extern int optind;
|
||||
extern char *optarg;
|
||||
int errflg;
|
||||
int c;
|
||||
|
||||
set_wrfileopt(0);
|
||||
(void)strcat(options, get_wrfileopt());
|
||||
(void)strcat(options, LOCALOPT);
|
||||
errflg = 0;
|
||||
filename = "";
|
||||
macname[0] = 0;
|
||||
|
||||
while((c = getopt(argc, argv, options)) != EOF) {
|
||||
if(!wrfileopt((char)c)) {
|
||||
switch(c) {
|
||||
case 'l':
|
||||
listmode++;
|
||||
break;
|
||||
case 'v':
|
||||
verbose++;
|
||||
break;
|
||||
case 'i':
|
||||
info_only++;
|
||||
break;
|
||||
case 'c':
|
||||
uneven_lines++;
|
||||
break;
|
||||
case 'n':
|
||||
backtrans(macname, optarg);
|
||||
break;
|
||||
case '?':
|
||||
errflg++;
|
||||
break;
|
||||
case 'H':
|
||||
give_wrfileopt();
|
||||
(void)fprintf(stderr, "Hexbin specific options:\n");
|
||||
(void)fprintf(stderr,
|
||||
"-i:\tgive information only, do not convert\n");
|
||||
(void)fprintf(stderr, "-l:\tgive listing\n");
|
||||
(void)fprintf(stderr,
|
||||
"-v:\tgive verbose listing, including lines skipped\n");
|
||||
(void)fprintf(stderr,
|
||||
"-c:\tdo not check for equal line lengths\n");
|
||||
(void)fprintf(stderr, "-n nm:\tname to be generated\n");
|
||||
(void)fprintf(stderr,
|
||||
"-V:\tgive information about this version\n");
|
||||
(void)fprintf(stderr, "-H:\tthis message\n");
|
||||
(void)fprintf(stderr, "Default is silent conversion\n");
|
||||
exit(0);
|
||||
case 'V':
|
||||
(void)fprintf(stderr, "Version %s, ", VERSION);
|
||||
(void)fprintf(stderr, "patchlevel %d", PATCHLEVEL);
|
||||
(void)fprintf(stderr, "%s.\n", get_mina());
|
||||
(void)fprintf(stderr, "Hexified files recognized:\n");
|
||||
#ifdef DL
|
||||
(void)fprintf(stderr, "\tDownload (.dl)\n");
|
||||
#endif /* DL */
|
||||
#ifdef HECX
|
||||
(void)fprintf(stderr, "\tBinHex 2.0 (.hex)\n");
|
||||
(void)fprintf(stderr, "\tBinHex 3.0 (.hcx)\n");
|
||||
#endif /* HECX */
|
||||
#ifdef HQX
|
||||
(void)fprintf(stderr, "\tBinHex 4.0 (.hqx)\n");
|
||||
#endif /* HQX */
|
||||
#ifdef MU
|
||||
(void)fprintf(stderr, "\tUUTool (.mu)\n");
|
||||
#endif /* MU */
|
||||
exit(0);
|
||||
}
|
||||
}
|
||||
}
|
||||
if(errflg) {
|
||||
usage();
|
||||
exit(1);
|
||||
}
|
||||
if(info_only || verbose) {
|
||||
listmode++;
|
||||
}
|
||||
|
||||
do {
|
||||
if(optind == argc) {
|
||||
filename = "-";
|
||||
} else {
|
||||
filename = argv[optind];
|
||||
optind++;
|
||||
#ifdef SCAN
|
||||
do_idf(filename, UNIX_NAME);
|
||||
#endif /* SCAN */
|
||||
}
|
||||
do_files(filename, macname);
|
||||
} while(optind < argc);
|
||||
exit(0);
|
||||
/* NOTREACHED */
|
||||
}
|
||||
|
||||
static char *extensions[] = {
|
||||
#ifdef DL
|
||||
".dl",
|
||||
#endif /* DL */
|
||||
#ifdef HECX
|
||||
".hex",
|
||||
".Hex",
|
||||
".hcx",
|
||||
".Hcx",
|
||||
#endif /* HECX */
|
||||
#ifdef HQX
|
||||
".hqx",
|
||||
".Hqx",
|
||||
#endif /* HQX */
|
||||
#ifdef MU
|
||||
".mu",
|
||||
#endif /* MU */
|
||||
"",
|
||||
NULL
|
||||
};
|
||||
|
||||
static void do_files(filename, macname)
|
||||
char *filename; /* input file name -- extension optional */
|
||||
char *macname; /* name to use on the mac side of things */
|
||||
{
|
||||
char namebuf[256];
|
||||
char **ep;
|
||||
struct stat stbuf;
|
||||
long curtime;
|
||||
int qformat;
|
||||
int again;
|
||||
|
||||
if(filename[0] == '-') {
|
||||
ifp = stdin;
|
||||
filename = "stdin";
|
||||
} else {
|
||||
/* find input file and open it */
|
||||
for(ep = extensions; *ep != NULL; ep++) {
|
||||
(void)sprintf(namebuf, "%s%s", filename, *ep);
|
||||
if(stat(namebuf, &stbuf) == 0) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
if(*ep == NULL) {
|
||||
perror(namebuf);
|
||||
exit(1);
|
||||
}
|
||||
ifp = fopen(namebuf, "r");
|
||||
if(ifp == NULL) {
|
||||
perror(namebuf);
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
again = 0;
|
||||
nexttry:
|
||||
if(ifp == stdin) {
|
||||
curtime = (long)time((time_t *)0) + TIMEDIFF;
|
||||
mh.m_createtime = curtime;
|
||||
mh.m_modifytime = curtime;
|
||||
} else {
|
||||
mh.m_createtime = stbuf.st_mtime + TIMEDIFF;
|
||||
mh.m_modifytime = stbuf.st_mtime + TIMEDIFF;
|
||||
}
|
||||
|
||||
qformat = find_header(again); /* eat mailer header &cetera, intuit format */
|
||||
|
||||
switch (qformat) {
|
||||
#ifdef DL
|
||||
case form_dl:
|
||||
dl(macname, filename);
|
||||
break;
|
||||
#endif /* DL */
|
||||
#ifdef HECX
|
||||
case form_hecx:
|
||||
hecx(macname, filename);
|
||||
break;
|
||||
#endif /* HECX */
|
||||
#ifdef HQX
|
||||
case form_hqx:
|
||||
hqx(macname);
|
||||
again = 1;
|
||||
goto nexttry;
|
||||
#endif /* HQX */
|
||||
#ifdef MU
|
||||
case form_mu:
|
||||
mu(macname);
|
||||
again = 1;
|
||||
goto nexttry;
|
||||
#endif /* MU */
|
||||
default:
|
||||
break;
|
||||
}
|
||||
(void)fclose(ifp);
|
||||
}
|
||||
|
||||
/* eat characters until header detected, return which format */
|
||||
static int find_header(again)
|
||||
int again;
|
||||
{
|
||||
int c, dl_start, llen;
|
||||
char *cp;
|
||||
char header[INFOBYTES];
|
||||
int ds, rs;
|
||||
|
||||
if(again && was_macbin) {
|
||||
while(to_read-- > 0) {
|
||||
c = fgetc(ifp);
|
||||
}
|
||||
}
|
||||
was_macbin = 0;
|
||||
c = fgetc(ifp);
|
||||
(void)ungetc(c, ifp);
|
||||
if(c == 0) {
|
||||
was_macbin = 1;
|
||||
if(fread(header, 1, INFOBYTES, ifp) != INFOBYTES) {
|
||||
(void)fprintf(stderr, "Premature EOF\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: Premature EOF");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
ds = get4(header + I_DLENOFF);
|
||||
rs = get4(header + I_RLENOFF);
|
||||
ds = (((ds + 127) >> 7) << 7);
|
||||
rs = (((rs + 127) >> 7) << 7);
|
||||
to_read = ds + rs;
|
||||
if(strncmp(header + I_TYPEOFF, "TEXT", 4)) {
|
||||
(void)fprintf(stderr, "This file is not a proper BinHexed file.\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: not a proper BinHexed file");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
if(listmode) {
|
||||
(void)fprintf(stderr, "This file is probably packed by ");
|
||||
if(!strncmp(header + I_AUTHOFF, "BNHQ", 4)) {
|
||||
(void)fprintf(stderr, "\"BinHex\"");
|
||||
} else if(!strncmp(header + I_AUTHOFF, "BthX", 4)) {
|
||||
(void)fprintf(stderr, "\"BinHqx\"");
|
||||
} else if(!strncmp(header + I_AUTHOFF, "BnHq", 4)) {
|
||||
(void)fprintf(stderr, "\"StuffIt\"");
|
||||
} else if(!strncmp(header + I_AUTHOFF, "ttxt", 4)) {
|
||||
(void)fprintf(stderr, "\"Compactor\"");
|
||||
} else if(!strncmp(header + I_AUTHOFF, "BSWU", 4)) {
|
||||
(void)fprintf(stderr, "\"UUTool\"");
|
||||
} else {
|
||||
(void)fprintf(stderr, "an unknown program");
|
||||
}
|
||||
(void)fprintf(stderr, ".\n");
|
||||
}
|
||||
}
|
||||
/* look for "(This file ...)" or "(Convert with...)" line. */
|
||||
/* or for "begin " */
|
||||
/* dl format starts with a line containing only the symbols '@' to 'O',
|
||||
or '|'. */
|
||||
while(readline()) {
|
||||
llen = strlen(line);
|
||||
#ifdef HQX
|
||||
if((strncmp(line, "(This file", 10) == 0) ||
|
||||
(strncmp(line, "(Convert with", 13) == 0)) {
|
||||
if(verbose) {
|
||||
(void)fprintf(stderr, "Skip:%s\n", line);
|
||||
}
|
||||
break;
|
||||
}
|
||||
#endif /* HQX */
|
||||
#ifdef MU
|
||||
if(strncmp(line, "begin ", 6) == 0) {
|
||||
return form_mu;
|
||||
}
|
||||
#endif /* MU */
|
||||
#ifdef DL
|
||||
/* Do not allow bogus false starts */
|
||||
if(llen > 40 && (llen & 1) == 0) {
|
||||
dl_start = 1;
|
||||
for(cp = &line[0]; *cp != 0; cp++) {
|
||||
if((*cp < '@' || *cp > 'O') && *cp != '|') {
|
||||
dl_start = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if(dl_start && cp > &line[1]) {
|
||||
return form_dl;
|
||||
}
|
||||
}
|
||||
#endif /* DL */
|
||||
if(llen != 0 && verbose) {
|
||||
(void)fprintf(stderr, "Skip:%s\n", line);
|
||||
}
|
||||
}
|
||||
while(readline()) {
|
||||
switch (line[0]) {
|
||||
#ifdef HQX
|
||||
case ':':
|
||||
return form_hqx;
|
||||
#endif /* HQX */
|
||||
#ifdef HECX
|
||||
case '#':
|
||||
return form_hecx;
|
||||
#endif /* HECX */
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if(!again) {
|
||||
(void)fprintf(stderr, "unexpected EOF\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: unexpected EOF");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
return form_none;
|
||||
}
|
||||
|
||||
static void usage()
|
||||
{
|
||||
(void)fprintf(stderr, "Usage: hexbin [-%s] [filenames]\n", options);
|
||||
(void)fprintf(stderr, "Use \"hexbin -H\" for help.\n");
|
||||
}
|
||||
|
11
hexbin/hexbin.h
Executable file
11
hexbin/hexbin.h
Executable file
@ -0,0 +1,11 @@
|
||||
#define DL /* recognize dl format */
|
||||
#define HECX /* recognize hex and hcx formats */
|
||||
#define HQX /* recognize hqx format */
|
||||
#define MU /* recognize mu format */
|
||||
|
||||
#define form_dl 0
|
||||
#define form_hecx 1
|
||||
#define form_hqx 2
|
||||
#define form_mu 3
|
||||
#define form_none (-1)
|
||||
|
396
hexbin/hqx.c
Executable file
396
hexbin/hqx.c
Executable file
@ -0,0 +1,396 @@
|
||||
#include "hexbin.h"
|
||||
#ifdef HQX
|
||||
#include "globals.h"
|
||||
#include "readline.h"
|
||||
#include "crc.h"
|
||||
#include "buffer.h"
|
||||
#include "../fileio/machdr.h"
|
||||
#include "../fileio/wrfile.h"
|
||||
#include "../util/util.h"
|
||||
#include "printhdr.h"
|
||||
|
||||
extern void exit();
|
||||
|
||||
static void get_header();
|
||||
static void oflush();
|
||||
static int getq();
|
||||
static long get2q();
|
||||
static long get4q();
|
||||
static getqbuf();
|
||||
|
||||
static char *g_macname;
|
||||
|
||||
/* New stuff which hopes to improve the speed. */
|
||||
|
||||
#define RUNCHAR 0x90
|
||||
|
||||
#define DONE 0x7F
|
||||
#define SKIP 0x7E
|
||||
#define FAIL 0x7D
|
||||
|
||||
static char lookup[256] = {
|
||||
/* ^@ ^A ^B ^C ^D ^E ^F ^G */
|
||||
/* 0*/ FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
/* \b \t \n ^K ^L \r ^N ^O */
|
||||
/* 1*/ FAIL, FAIL, SKIP, FAIL, FAIL, SKIP, FAIL, FAIL,
|
||||
/* ^P ^Q ^R ^S ^T ^U ^V ^W */
|
||||
/* 2*/ FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
/* ^X ^Y ^Z ^[ ^\ ^] ^^ ^_ */
|
||||
/* 3*/ FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
/* ! " # $ % & ' */
|
||||
/* 4*/ FAIL, 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06,
|
||||
/* ( ) * + , - . / */
|
||||
/* 5*/ 0x07, 0x08, 0x09, 0x0A, 0x0B, 0x0C, FAIL, FAIL,
|
||||
/* 0 1 2 3 4 5 6 7 */
|
||||
/* 6*/ 0x0D, 0x0E, 0x0F, 0x10, 0x11, 0x12, 0x13, FAIL,
|
||||
/* 8 9 : ; < = > ? */
|
||||
/* 7*/ 0x14, 0x15, DONE, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
/* @ A B C D E F G */
|
||||
/* 8*/ 0x16, 0x17, 0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D,
|
||||
/* H I J K L M N O */
|
||||
/* 9*/ 0x1E, 0x1F, 0x20, 0x21, 0x22, 0x23, 0x24, FAIL,
|
||||
/* P Q R S T U V W */
|
||||
/*10*/ 0x25, 0x26, 0x27, 0x28, 0x29, 0x2A, 0x2B, FAIL,
|
||||
/* X Y Z [ \ ] ^ _ */
|
||||
/*11*/ 0x2C, 0x2D, 0x2E, 0x2F, FAIL, FAIL, FAIL, FAIL,
|
||||
/* ` a b c d e f g */
|
||||
/*12*/ 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, FAIL,
|
||||
/* h i j k l m n o */
|
||||
/*13*/ 0x37, 0x38, 0x39, 0x3A, 0x3B, 0x3C, FAIL, FAIL,
|
||||
/* p q r s t u v w */
|
||||
/*14*/ 0x3D, 0x3E, 0x3F, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
/* x y z { | } ~ ^? */
|
||||
/*15*/ FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
/*16*/ FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
|
||||
};
|
||||
|
||||
static int stop = 0;
|
||||
|
||||
static unsigned char obuf[BUFSIZ];
|
||||
static unsigned char *op = obuf;
|
||||
static unsigned char *oq;
|
||||
|
||||
#define S_HEADER 0
|
||||
#define S_DATAOPEN 1
|
||||
#define S_DATAWRITE 2
|
||||
#define S_DATAC1 3
|
||||
#define S_DATAC2 4
|
||||
#define S_RSRCOPEN 5
|
||||
#define S_RSRCWRITE 6
|
||||
#define S_RSRCC1 7
|
||||
#define S_RSRCC2 8
|
||||
#define S_EXCESS 9
|
||||
|
||||
static int ostate = S_HEADER;
|
||||
|
||||
static unsigned long calc_crc;
|
||||
static unsigned long file_crc;
|
||||
|
||||
static long todo;
|
||||
|
||||
#define output(c) { *op++ = (c); if(op >= &obuf[BUFSIZ]) oflush(); }
|
||||
|
||||
void hqx(macname)
|
||||
char *macname;
|
||||
{
|
||||
int n, normlen, c;
|
||||
register char *in, *out;
|
||||
register int b6, b8, data, lastc = 0;
|
||||
char state68 = 0, run = 0, linestate, first = 1;
|
||||
|
||||
g_macname = macname;
|
||||
|
||||
ostate = S_HEADER;
|
||||
stop = 0;
|
||||
|
||||
while(!stop) {
|
||||
n = strlen((char *)line);
|
||||
while(n > 0 && line[n - 1] == ' ') {
|
||||
n--;
|
||||
}
|
||||
out = line+n;
|
||||
if(uneven_lines) {
|
||||
goto skipcheck;
|
||||
}
|
||||
if(first) {
|
||||
normlen = n;
|
||||
}
|
||||
/* Check line for intermediate garbage */
|
||||
linestate = SKIP;
|
||||
for(in = line; in < out; in++) {
|
||||
if((linestate = lookup[*in & 0xff]) == FAIL ||
|
||||
((linestate == DONE) && !first)) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
if(linestate != FAIL && n != normlen && linestate != DONE) {
|
||||
c = fgetc(ifp);
|
||||
(void)ungetc(c, ifp);
|
||||
if(lookup[c] == DONE) {
|
||||
linestate = DONE;
|
||||
}
|
||||
}
|
||||
if(linestate == FAIL || (n != normlen && linestate != DONE)) {
|
||||
if(verbose && n > 0) {
|
||||
*out = 0;
|
||||
(void)fprintf(stderr, "Skip:%s\n", line);
|
||||
}
|
||||
if(readline()) {
|
||||
continue;
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
skipcheck:
|
||||
in = line;
|
||||
do {
|
||||
if((b6 = lookup[*in & 0xff]) >= 64) {
|
||||
switch (b6) {
|
||||
case DONE:
|
||||
first = !first;
|
||||
if(first) {
|
||||
goto done;
|
||||
}
|
||||
case SKIP:
|
||||
break;
|
||||
default:
|
||||
if(uneven_lines) {
|
||||
break;
|
||||
}
|
||||
(void)fprintf(stderr, "bad char '%c'(%d)\n", *in, *in);
|
||||
goto done;
|
||||
}
|
||||
} else {
|
||||
/* Pack 6 bits to 8 bits */
|
||||
switch (state68++) {
|
||||
case 0:
|
||||
b8 = b6<<2;
|
||||
continue; /* No data byte */
|
||||
case 1:
|
||||
data = b8 | (b6>>4);
|
||||
b8 = (b6&0xF) << 4;
|
||||
break;
|
||||
case 2:
|
||||
data = b8 | (b6>>2);
|
||||
b8 = (b6&0x3) << 6;
|
||||
break;
|
||||
case 3:
|
||||
data = b8 | b6;
|
||||
state68 = 0;
|
||||
break;
|
||||
}
|
||||
if(!run) {
|
||||
if(data == RUNCHAR) {
|
||||
run = 1;
|
||||
} else {
|
||||
output(lastc = data);
|
||||
}
|
||||
}
|
||||
else {
|
||||
if(data == 0) {
|
||||
output(lastc = RUNCHAR);
|
||||
} else {
|
||||
while(--data > 0) {
|
||||
output(lastc);
|
||||
}
|
||||
}
|
||||
run = 0;
|
||||
}
|
||||
}
|
||||
} while(++in < out);
|
||||
if(!stop) {
|
||||
if(!readline()) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
done:
|
||||
oflush();
|
||||
if(!stop && ostate != S_EXCESS) {
|
||||
(void)fprintf(stderr, "premature EOF\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: premature EOF");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
end_put();
|
||||
print_header2(verbose);
|
||||
}
|
||||
|
||||
static void get_header()
|
||||
{
|
||||
int n;
|
||||
unsigned long calc_crc, file_crc;
|
||||
|
||||
crc = INITCRC; /* compute a crc for the header */
|
||||
|
||||
for(n = 0; n < INFOBYTES; n++) {
|
||||
info[n] = 0;
|
||||
}
|
||||
n = getq(); /* namelength */
|
||||
n++; /* must read trailing null also */
|
||||
getqbuf(trname, n); /* read name */
|
||||
if(g_macname[0] == '\0') {
|
||||
g_macname = trname;
|
||||
}
|
||||
|
||||
n = strlen(g_macname);
|
||||
if(n > F_NAMELEN) {
|
||||
n = F_NAMELEN;
|
||||
}
|
||||
(void)strncpy(mh.m_name, g_macname, n);
|
||||
mh.m_name[n] = '\0';
|
||||
|
||||
getqbuf(mh.m_type, 4);
|
||||
getqbuf(mh.m_author, 4);
|
||||
mh.m_flags = get2q();
|
||||
mh.m_datalen = get4q();
|
||||
mh.m_rsrclen = get4q();
|
||||
|
||||
calc_crc = crc;
|
||||
file_crc = get2q();
|
||||
verify_crc(calc_crc, file_crc);
|
||||
if(listmode) {
|
||||
(void)fprintf(stderr, "This file is in \"hqx\" format.\n");
|
||||
}
|
||||
transname(mh.m_name, trname, n);
|
||||
define_name(trname);
|
||||
print_header0(0);
|
||||
print_header1(0, verbose);
|
||||
info[I_NAMEOFF] = n;
|
||||
(void)strncpy(info + I_NAMEOFF + 1, mh.m_name, n);
|
||||
(void)strncpy(info + I_TYPEOFF, mh.m_type, 4);
|
||||
(void)strncpy(info + I_AUTHOFF, mh.m_author, 4);
|
||||
put2(info + I_FLAGOFF, (unsigned long)mh.m_flags);
|
||||
put4(info + I_DLENOFF, (unsigned long)mh.m_datalen);
|
||||
put4(info + I_RLENOFF, (unsigned long)mh.m_rsrclen);
|
||||
put4(info + I_CTIMOFF, (unsigned long)mh.m_createtime);
|
||||
put4(info + I_MTIMOFF, (unsigned long)mh.m_modifytime);
|
||||
}
|
||||
|
||||
static void oflush()
|
||||
{
|
||||
int n, i;
|
||||
|
||||
oq = obuf;
|
||||
while(oq < op && !stop) {
|
||||
switch (ostate) {
|
||||
case S_HEADER:
|
||||
get_header();
|
||||
++ostate;
|
||||
break;
|
||||
case S_DATAOPEN:
|
||||
set_put(1);
|
||||
todo = mh.m_datalen;
|
||||
crc = INITCRC;
|
||||
++ostate;
|
||||
break;
|
||||
case S_RSRCOPEN:
|
||||
set_put(0);
|
||||
todo = mh.m_rsrclen;
|
||||
crc = INITCRC;
|
||||
++ostate;
|
||||
break;
|
||||
case S_DATAWRITE:
|
||||
case S_RSRCWRITE:
|
||||
n = op-oq;
|
||||
if(n > todo) {
|
||||
n = todo;
|
||||
}
|
||||
for(i = 0; i < n; i++) {
|
||||
put_byte((char)(oq[i]));
|
||||
}
|
||||
comp_q_crc_n(oq, oq+n);
|
||||
oq += n;
|
||||
todo -= n;
|
||||
if(todo <= 0) {
|
||||
++ostate;
|
||||
}
|
||||
break;
|
||||
case S_DATAC1:
|
||||
case S_RSRCC1:
|
||||
calc_crc = crc;
|
||||
file_crc = getq() << 8;
|
||||
++ostate;
|
||||
break;
|
||||
case S_DATAC2:
|
||||
case S_RSRCC2:
|
||||
/* Skip crc bytes */
|
||||
file_crc |= getq();
|
||||
verify_crc(calc_crc, file_crc);
|
||||
++ostate;
|
||||
break;
|
||||
case S_EXCESS:
|
||||
(void)fprintf(stderr, "%d excess bytes ignored\n", op-oq);
|
||||
oq = op;
|
||||
break;
|
||||
}
|
||||
}
|
||||
op = obuf;
|
||||
}
|
||||
|
||||
static int getq()
|
||||
{
|
||||
int c;
|
||||
|
||||
if(oq >= op) {
|
||||
(void)fprintf(stderr, "premature EOF\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: premature EOF");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
c = *oq++ & 0xff;
|
||||
comp_q_crc((unsigned)c);
|
||||
return c;
|
||||
}
|
||||
|
||||
/* get2q(); q format -- read 2 bytes from input, return short */
|
||||
static long get2q()
|
||||
{
|
||||
short high = getq() << 8;
|
||||
return high | getq();
|
||||
}
|
||||
|
||||
/* get4q(); q format -- read 4 bytes from input, return long */
|
||||
static long get4q()
|
||||
{
|
||||
int i;
|
||||
long value = 0;
|
||||
|
||||
for(i = 0; i < 4; i++) {
|
||||
value = (value<<8) | getq();
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
/* getqbuf(); q format -- read n characters from input into buf */
|
||||
static getqbuf(buf, n)
|
||||
char *buf;
|
||||
int n;
|
||||
{
|
||||
int i;
|
||||
|
||||
for(i = 0; i < n; i++) {
|
||||
*buf++ = getq();
|
||||
}
|
||||
}
|
||||
#else /* HQX */
|
||||
int hqx; /* keep lint and some compilers happy */
|
||||
#endif /* HQX */
|
||||
|
35
hexbin/hqx.diff
Executable file
35
hexbin/hqx.diff
Executable file
@ -0,0 +1,35 @@
|
||||
*** hqx.c Mon Mar 9 21:36:57 1992
|
||||
--- n.hqx.c Mon Mar 9 22:07:53 1992
|
||||
***************
|
||||
*** 108,114 ****
|
||||
void hqx(macname)
|
||||
char *macname;
|
||||
{
|
||||
! int n, normlen;
|
||||
register char *in, *out;
|
||||
register int b6, b8, data, lastc = 0;
|
||||
char state68 = 0, run = 0, linestate, first = 1;
|
||||
--- 108,114 ----
|
||||
void hqx(macname)
|
||||
char *macname;
|
||||
{
|
||||
! int n, normlen, c;
|
||||
register char *in, *out;
|
||||
register int b6, b8, data, lastc = 0;
|
||||
char state68 = 0, run = 0, linestate, first = 1;
|
||||
***************
|
||||
*** 136,141 ****
|
||||
--- 136,148 ----
|
||||
if((linestate = lookup[*in & 0xff]) == FAIL ||
|
||||
((linestate == DONE) && !first)) {
|
||||
break;
|
||||
+ }
|
||||
+ }
|
||||
+ if(linestate != FAIL && n != normlen && linestate != DONE) {
|
||||
+ c = fgetc(ifp);
|
||||
+ (void)ungetc(c, ifp);
|
||||
+ if(lookup[c] == DONE) {
|
||||
+ linestate = DONE;
|
||||
}
|
||||
}
|
||||
if(linestate == FAIL || (n != normlen && linestate != DONE)) {
|
130
hexbin/makefile
Executable file
130
hexbin/makefile
Executable file
@ -0,0 +1,130 @@
|
||||
CFLAGS= -O $(CF)
|
||||
|
||||
SRCS = hexbin.c \
|
||||
dl.c \
|
||||
hecx.c \
|
||||
hqx.c \
|
||||
mu.c \
|
||||
buffer.c \
|
||||
crc.c \
|
||||
readline.c \
|
||||
printhdr.c \
|
||||
globals.c
|
||||
|
||||
OBJS = hexbin.o \
|
||||
dl.o \
|
||||
hecx.o \
|
||||
hqx.o \
|
||||
mu.o \
|
||||
buffer.o \
|
||||
crc.o \
|
||||
readline.o \
|
||||
printhdr.o \
|
||||
globals.o
|
||||
|
||||
LIB = ../crc/libcrc.a
|
||||
TNAME = ../util/transname
|
||||
BNAME = ../util/backtrans
|
||||
UNAME = ../util/util
|
||||
ONAME = ../fileio/wrfile
|
||||
GNAME = ../fileio/fileglob
|
||||
XOBJS = $(TNAME).o $(BNAME).o $(UNAME).o $(ONAME).o $(GNAME).o
|
||||
XSRCS = $(TNAME).c $(BNAME).c $(UNAME).c $(ONAME).c $(GNAME).c
|
||||
CRCS = ../crc/binhex.c
|
||||
|
||||
hexbin: $(OBJS) $(LIB) $(XOBJS)
|
||||
$(CC) $(CFLAGS) -o hexbin $(OBJS) $(XOBJS) $(LIB)
|
||||
|
||||
$(LIB): ../crc/makecrc.c
|
||||
(cd ../crc; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
$(TNAME).o: $(TNAME).c
|
||||
(cd ../util; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
$(BNAME).o: $(BNAME).c
|
||||
(cd ../util; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
$(UNAME).o: $(UNAME).c
|
||||
(cd ../util; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
$(ONAME).o: $(ONAME).c
|
||||
(cd ../fileio; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
$(GNAME).o: $(GNAME).c
|
||||
(cd ../fileio; make CC=$(CC) CF="$(CF)" )
|
||||
|
||||
lint:
|
||||
lint $(CF) $(LFLAGS) $(SRCS) $(XSRCS) $(CRCS)
|
||||
|
||||
clean:
|
||||
-rm -f *.o
|
||||
|
||||
clobber:clean
|
||||
-rm -f hexbin
|
||||
|
||||
hexbin.o: globals.h
|
||||
hexbin.o: crc.h
|
||||
hexbin.o: readline.h
|
||||
hexbin.o: ../util/masks.h
|
||||
hexbin.o: ../util/util.h
|
||||
hexbin.o: ../util/patchlevel.h
|
||||
hexbin.o: ../fileio/wrfile.h
|
||||
hexbin.o: ../fileio/wrfileopt.h
|
||||
hexbin.o: ../fileio/machdr.h
|
||||
hexbin.o: ../fileio/kind.h
|
||||
hexbin.o: ../util/curtime.h
|
||||
hexbin.o: hexbin.h
|
||||
dl.o: hexbin.h
|
||||
dl.o: globals.h
|
||||
dl.o: crc.h
|
||||
dl.o: readline.h
|
||||
dl.o: ../fileio/machdr.h
|
||||
dl.o: ../fileio/wrfile.h
|
||||
dl.o: ../util/util.h
|
||||
dl.o: buffer.h
|
||||
dl.o: printhdr.h
|
||||
hecx.o: hexbin.h
|
||||
hecx.o: globals.h
|
||||
hecx.o: crc.h
|
||||
hecx.o: readline.h
|
||||
hecx.o: ../util/masks.h
|
||||
hecx.o: ../util/util.h
|
||||
hecx.o: ../fileio/machdr.h
|
||||
hecx.o: ../fileio/wrfile.h
|
||||
hecx.o: buffer.h
|
||||
hecx.o: printhdr.h
|
||||
hqx.o: hexbin.h
|
||||
hqx.o: globals.h
|
||||
hqx.o: readline.h
|
||||
hqx.o: crc.h
|
||||
hqx.o: buffer.h
|
||||
hqx.o: ../fileio/machdr.h
|
||||
hqx.o: ../fileio/wrfile.h
|
||||
hqx.o: ../util/util.h
|
||||
hqx.o: printhdr.h
|
||||
mu.o: hexbin.h
|
||||
mu.o: globals.h
|
||||
mu.o: readline.h
|
||||
mu.o: ../util/masks.h
|
||||
mu.o: ../util/util.h
|
||||
mu.o: ../fileio/machdr.h
|
||||
mu.o: ../fileio/wrfile.h
|
||||
mu.o: buffer.h
|
||||
mu.o: printhdr.h
|
||||
buffer.o: globals.h
|
||||
buffer.o: ../util/util.h
|
||||
buffer.o: buffer.h
|
||||
buffer.o: ../fileio/wrfile.h
|
||||
crc.o: hexbin.h
|
||||
crc.o: crc.h
|
||||
crc.o: ../util/masks.h
|
||||
crc.o: globals.h
|
||||
readline.o: readline.h
|
||||
readline.o: globals.h
|
||||
printhdr.o: printhdr.h
|
||||
printhdr.o: globals.h
|
||||
globals.o: globals.h
|
||||
globals.o: ../fileio/machdr.h
|
||||
globals.o: ../fileio/wrfile.h
|
||||
globals.o: ../fileio/kind.h
|
||||
|
225
hexbin/mu.c
Executable file
225
hexbin/mu.c
Executable file
@ -0,0 +1,225 @@
|
||||
#include "hexbin.h"
|
||||
#ifdef MU
|
||||
#include "globals.h"
|
||||
#include "readline.h"
|
||||
#include "../util/masks.h"
|
||||
#include "../util/util.h"
|
||||
#include "../fileio/machdr.h"
|
||||
#include "../fileio/wrfile.h"
|
||||
#include "buffer.h"
|
||||
#include "printhdr.h"
|
||||
|
||||
extern void exit();
|
||||
|
||||
static void do_mu_fork();
|
||||
static int mu_comp_to_bin();
|
||||
static int mu_convert();
|
||||
|
||||
/* mu format -- process .mu files */
|
||||
void mu(macname)
|
||||
char *macname;
|
||||
{
|
||||
int n;
|
||||
|
||||
for(n = 0; n < INFOBYTES; n++) {
|
||||
info[n] = 0;
|
||||
}
|
||||
|
||||
/* set up name for output files */
|
||||
if(macname[0] == '\0') {
|
||||
n = 0;
|
||||
while(line[n] != '"') {
|
||||
n++;
|
||||
}
|
||||
macname = line + n + 1;
|
||||
line[strlen(line) - 1] = 0;
|
||||
}
|
||||
n = strlen(macname);
|
||||
if(n > F_NAMELEN) {
|
||||
n = F_NAMELEN;
|
||||
}
|
||||
(void)strncpy(mh.m_name, macname, n);
|
||||
mh.m_name[n] = '\0';
|
||||
info[I_NAMEOFF] = n;
|
||||
(void)strncpy(info + I_NAMEOFF + 1, mh.m_name, n);
|
||||
|
||||
if(listmode) {
|
||||
(void)fprintf(stderr, "This file is in \"mu\" format.\n");
|
||||
}
|
||||
transname(mh.m_name, trname, n);
|
||||
define_name(trname);
|
||||
print_header0(0);
|
||||
set_put(0);
|
||||
set_put(1);
|
||||
do_mu_fork();
|
||||
mh.m_datalen = data_size;
|
||||
if(!readline()) {
|
||||
(void)fprintf(stderr, "Premature EOF\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: Premature EOF");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
if(strncmp(line, "begin ", 6)) {
|
||||
(void)fprintf(stderr, "No UU header found.\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: No UU header found");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
if(!strncmp(line + 10, " .rsrc", 6)) {
|
||||
set_put(0);
|
||||
do_mu_fork();
|
||||
mh.m_rsrclen = rsrc_size;
|
||||
if(!readline()) {
|
||||
(void)fprintf(stderr, "Premature EOF\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: Premature EOF");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
if(strncmp(line, "begin ", 6)) {
|
||||
(void)fprintf(stderr, "No UU header found.\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: No UU header found");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
} else {
|
||||
mh.m_rsrclen = 0;
|
||||
}
|
||||
if(strncmp(line + 10, " .finfo", 7)) {
|
||||
(void)fprintf(stderr, "No finder info found.\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: No finder info found");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
if(!readline()) {
|
||||
(void)fprintf(stderr, "Premature EOF\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: Premature EOF");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
(void)mu_convert(line, info + I_TYPEOFF);
|
||||
if(!readline()) {
|
||||
(void)fprintf(stderr, "Premature EOF\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: Premature EOF");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
if(mu_convert(line, line)) {
|
||||
(void)fprintf(stderr, "Long finderinfo.\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: Long finderinfo");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
if(!readline()) {
|
||||
(void)fprintf(stderr, "Premature EOF\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: Premature EOF");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
if(strncmp(line, "end", 3)) {
|
||||
(void)fprintf(stderr, "\"end\" line missing.\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: \"end\" line missing");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
|
||||
(void)strncpy(mh.m_type, info + I_TYPEOFF, 4);
|
||||
(void)strncpy(mh.m_author, info + I_AUTHOFF, 4);
|
||||
print_header1(0, 0);
|
||||
put4(info + I_DLENOFF, (unsigned long)mh.m_datalen);
|
||||
put4(info + I_RLENOFF, (unsigned long)mh.m_rsrclen);
|
||||
put4(info + I_CTIMOFF, (unsigned long)mh.m_createtime);
|
||||
put4(info + I_MTIMOFF, (unsigned long)mh.m_modifytime);
|
||||
print_header2(0);
|
||||
end_put();
|
||||
}
|
||||
|
||||
static void do_mu_fork()
|
||||
{
|
||||
long newbytes;
|
||||
|
||||
while(readline()) {
|
||||
if(line[0] == 0) {
|
||||
continue;
|
||||
}
|
||||
newbytes = mu_comp_to_bin();
|
||||
if(newbytes != 0) {
|
||||
continue;
|
||||
}
|
||||
if(!readline()) {
|
||||
(void)fprintf(stderr, "Premature EOF\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: Premature EOF");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
if(strncmp(line, "end", 3)) {
|
||||
(void)fprintf(stderr, "\"end\" line missing.\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: \"end\" line missing");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
return;
|
||||
}
|
||||
(void)fprintf(stderr, "Premature EOF\n");
|
||||
#ifdef SCAN
|
||||
do_error("hexbin: Premature EOF");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
/*NOTREACHED*/
|
||||
}
|
||||
|
||||
static int mu_comp_to_bin()
|
||||
{
|
||||
char obuf[BUFSIZ];
|
||||
int outcount, n;
|
||||
|
||||
outcount = mu_convert(line, obuf);
|
||||
for(n = 0; n < outcount; n++) {
|
||||
put_byte(obuf[n]);
|
||||
}
|
||||
return outcount;
|
||||
}
|
||||
|
||||
#define SIXB(c) (((c)-0x20) & 0x3f)
|
||||
|
||||
static int mu_convert(ibuf, obuf)
|
||||
char *ibuf, *obuf;
|
||||
{
|
||||
register char *ip = ibuf;
|
||||
register char *op = obuf;
|
||||
register int n, outcount;
|
||||
int numread, incount;
|
||||
|
||||
numread = strlen(ip);
|
||||
outcount = SIXB(ip[0]);
|
||||
incount = ((outcount / 3) + 1) * 4;
|
||||
for(n = numread; n < incount; n++) { /* restore lost spaces */
|
||||
ip[n] = ' ';
|
||||
}
|
||||
ip++;
|
||||
|
||||
n = 0;
|
||||
while(n <= outcount) {
|
||||
*op++ = SIXB(ip[0]) << 2 | SIXB(ip[1]) >> 4;
|
||||
*op++ = SIXB(ip[1]) << 4 | SIXB(ip[2]) >> 2;
|
||||
*op++ = SIXB(ip[2]) << 6 | SIXB(ip[3]);
|
||||
ip += 4;
|
||||
n += 3;
|
||||
}
|
||||
return outcount;
|
||||
}
|
||||
#else /* MU */
|
||||
int mu; /* keep lint and some compilers happy */
|
||||
#endif /* MU */
|
||||
|
46
hexbin/printhdr.c
Executable file
46
hexbin/printhdr.c
Executable file
@ -0,0 +1,46 @@
|
||||
#include "printhdr.h"
|
||||
#include "globals.h"
|
||||
|
||||
/* print out header information in human-readable format */
|
||||
void print_header0(skip)
|
||||
int skip;
|
||||
{
|
||||
if(listmode) {
|
||||
(void)fprintf(stderr, "name=\"%s\", ", trname);
|
||||
if(skip) {
|
||||
(void)fprintf(stderr, "\n");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* print out header information in human-readable format */
|
||||
void print_header1(skip1, skip2)
|
||||
int skip1, skip2;
|
||||
{
|
||||
char ftype[5], fauth[5];
|
||||
|
||||
transname(mh.m_type, ftype, 4);
|
||||
transname(mh.m_author, fauth, 4);
|
||||
if(listmode) {
|
||||
if(skip1) {
|
||||
(void)fprintf(stderr, "\t");
|
||||
}
|
||||
(void)fprintf(stderr, "type=%4.4s, author=%4.4s, ", ftype, fauth);
|
||||
if(skip2) {
|
||||
(void)fprintf(stderr, "\n");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* print out header information in human-readable format */
|
||||
void print_header2(skip)
|
||||
{
|
||||
if(listmode) {
|
||||
if(skip) {
|
||||
(void)fprintf(stderr, "\t");
|
||||
}
|
||||
(void)fprintf(stderr, "data=%ld, rsrc=%ld\n",
|
||||
mh.m_datalen, mh.m_rsrclen);
|
||||
}
|
||||
}
|
||||
|
4
hexbin/printhdr.h
Executable file
4
hexbin/printhdr.h
Executable file
@ -0,0 +1,4 @@
|
||||
extern void print_header0();
|
||||
extern void print_header1();
|
||||
extern void print_header2();
|
||||
|
40
hexbin/readline.c
Executable file
40
hexbin/readline.c
Executable file
@ -0,0 +1,40 @@
|
||||
#include "globals.h"
|
||||
#include "readline.h"
|
||||
|
||||
char line[1024]; /* Allow a lot! */
|
||||
|
||||
/* Read a line. Allow termination by CR or LF or both. Also allow for
|
||||
a non-terminated line at end-of-file. Returns 1 if a line is read,
|
||||
0 otherwise. */
|
||||
int readline()
|
||||
{
|
||||
int ptr = 0, c;
|
||||
|
||||
while(1) {
|
||||
if(was_macbin && to_read-- <= 0) {
|
||||
c = EOF;
|
||||
} else {
|
||||
c = getc(ifp);
|
||||
}
|
||||
if(c == EOF || c == '\n' || c == '\r' || ptr == 1023) {
|
||||
break;
|
||||
}
|
||||
line[ptr++] = c;
|
||||
}
|
||||
line[ptr++] = 0;
|
||||
if(c == EOF) {
|
||||
if(ptr == 1) {
|
||||
return 0;
|
||||
} else {
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
c = getc(ifp);
|
||||
if(c != '\n' || c != '\r') {
|
||||
(void)ungetc(c, ifp);
|
||||
} else {
|
||||
to_read--;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
2
hexbin/readline.h
Executable file
2
hexbin/readline.h
Executable file
@ -0,0 +1,2 @@
|
||||
extern char line[];
|
||||
|
51
macunpack/arc.h
Executable file
51
macunpack/arc.h
Executable file
@ -0,0 +1,51 @@
|
||||
#define MAGIC1 0 /* Should be 0x1b, marks Mac extension */
|
||||
#define KIND 1 /* KIND == 0 marks end of archive */
|
||||
#define FNAME 2
|
||||
#define FILLER 33
|
||||
#define FTYPE 34
|
||||
#define FAUTH 38
|
||||
#define FINFO 42
|
||||
#define FDATA 50
|
||||
#define FRSRC 54
|
||||
#define FILLER 58
|
||||
#define MAGIC2 59 /* Should be 0x1a, true Arc header start */
|
||||
#define KIND2 60 /* Should be identical to KIND */
|
||||
#define FNAME2 61 /* A PC-ified version of the filename */
|
||||
#define SIZE 74
|
||||
#define DATE 78
|
||||
#define TIME 80
|
||||
#define CRC 82
|
||||
#define SIZE2 84 /* Not present if KIND == 1 */
|
||||
#define HEADERBYTES 88
|
||||
|
||||
typedef struct fileHdr { /* 84 or 88 bytes */
|
||||
char magic1;
|
||||
char kind;
|
||||
char fname[31];
|
||||
char filler; /* ??? */
|
||||
char ftype[4];
|
||||
char fauth[4];
|
||||
char finfo[8];
|
||||
unsigned long dataLength;
|
||||
unsigned long rsrcLength;
|
||||
char filler;
|
||||
char magic2;
|
||||
char kind2;
|
||||
char fname2[13];
|
||||
unsigned long size;
|
||||
unsigned short date;
|
||||
unsigned short time;
|
||||
unsigend short crc;
|
||||
unsigned long size2; /* Identical to size; this is wrong for Arc! */
|
||||
};
|
||||
|
||||
#define smallstored 1
|
||||
#define stored 2
|
||||
#define packed 3
|
||||
#define squeezed 4
|
||||
#define crunched1 5
|
||||
#define crunched2 6
|
||||
#define crunched3 7
|
||||
#define crunched4 8
|
||||
#define squashed 9
|
||||
|
68
macunpack/bin.c
Executable file
68
macunpack/bin.c
Executable file
@ -0,0 +1,68 @@
|
||||
#include "macunpack.h"
|
||||
#ifdef BIN
|
||||
#include "globals.h"
|
||||
#include "../fileio/machdr.h"
|
||||
#include "../fileio/wrfile.h"
|
||||
#include "../fileio/kind.h"
|
||||
#include "../util/util.h"
|
||||
#include "../util/masks.h"
|
||||
|
||||
extern void mcb();
|
||||
|
||||
void bin(header, data_size, UMcp)
|
||||
char *header;
|
||||
int data_size, UMcp;
|
||||
{
|
||||
char hdr[INFOBYTES];
|
||||
unsigned long rsrcLength, dataLength;
|
||||
|
||||
hdr[0] = getb(infp);
|
||||
(void)ungetc(hdr[0], infp);
|
||||
if(hdr[0] != 0) {
|
||||
if(!strncmp(header + I_AUTHOFF, "BnHq", 4) && hdr[0] == '(') {
|
||||
do_indent(indent);
|
||||
(void)fprintf(stderr, "Sorry, this is a fake BinHex 5.0 file. ");
|
||||
(void)fprintf(stderr, "Debinhex with hexbin first.\n");
|
||||
#ifdef SCAN
|
||||
do_error("macunpack: fake BinHex 5.0");
|
||||
#endif /* SCAN */
|
||||
} else {
|
||||
do_indent(indent);
|
||||
(void)fprintf(stderr, "Sorry, contents not recognized.\n");
|
||||
#ifdef SCAN
|
||||
do_error("macunpack: contents not recognized");
|
||||
#endif /* SCAN */
|
||||
}
|
||||
do_indent(indent);
|
||||
(void)fprintf(stderr, "Copying as a plain file.\n");
|
||||
#ifdef SCAN
|
||||
do_idf("", COPY);
|
||||
#endif /* SCAN */
|
||||
mcb(header, (unsigned long)in_data_size, (unsigned long)in_rsrc_size,
|
||||
in_ds + in_rs);
|
||||
ds_skip = 0;
|
||||
rs_skip = 0;
|
||||
in_ds = 0;
|
||||
in_rs = 0;
|
||||
return;
|
||||
}
|
||||
if(fread(hdr, 1, INFOBYTES - 1, infp) != INFOBYTES) {
|
||||
(void)fprintf(stderr, "Can't read file header\n");
|
||||
#ifdef SCAN
|
||||
do_error("macunpack: Can't read file header");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
rsrcLength = get4(hdr + I_RLENOFF);
|
||||
dataLength = get4(hdr + I_DLENOFF);
|
||||
if(UMcp) {
|
||||
/* Why this? Moreover, we are losing the bundle bit! */
|
||||
put4(hdr + I_RLENOFF, ++rsrcLength);
|
||||
put4(hdr + I_DLENOFF, ++dataLength);
|
||||
}
|
||||
mcb(hdr, rsrcLength, dataLength, data_size - INFOBYTES);
|
||||
}
|
||||
#else /* BIN */
|
||||
int bin; /* keep lint and some compilers happy */
|
||||
#endif /* BIN */
|
||||
|
BIN
macunpack/bin.o
Normal file
BIN
macunpack/bin.o
Normal file
Binary file not shown.
46
macunpack/bits_be.c
Executable file
46
macunpack/bits_be.c
Executable file
@ -0,0 +1,46 @@
|
||||
#include "../util/masks.h"
|
||||
#include "bits_be.h"
|
||||
|
||||
unsigned int bit_be_bitbuf;
|
||||
char *bit_be_filestart;
|
||||
int bit_be_inbytes;
|
||||
|
||||
static unsigned int bit_be_subbitbuf;
|
||||
static int bit_be_bitcount;
|
||||
|
||||
void bit_be_fillbuf(n) /* Shift bit_be_bitbuf n bits left, read n bits */
|
||||
int n;
|
||||
{
|
||||
bit_be_bitbuf <<= n;
|
||||
while (n > bit_be_bitcount) {
|
||||
bit_be_bitbuf |= bit_be_subbitbuf << (n -= bit_be_bitcount);
|
||||
if(bit_be_inbytes == 0) {
|
||||
bit_be_subbitbuf = 0;
|
||||
} else {
|
||||
bit_be_subbitbuf = *bit_be_filestart++ & BYTEMASK;
|
||||
bit_be_inbytes--;
|
||||
}
|
||||
bit_be_bitcount = 8;
|
||||
}
|
||||
bit_be_bitbuf |= bit_be_subbitbuf >> (bit_be_bitcount -= n);
|
||||
bit_be_bitbuf &= WORDMASK;
|
||||
}
|
||||
|
||||
unsigned int bit_be_getbits(n)
|
||||
int n;
|
||||
{
|
||||
unsigned int x;
|
||||
|
||||
x = bit_be_bitbuf >> (BITBUFSIZ - n);
|
||||
bit_be_fillbuf(n);
|
||||
return x;
|
||||
}
|
||||
|
||||
void bit_be_init_getbits()
|
||||
{
|
||||
bit_be_bitbuf = 0;
|
||||
bit_be_subbitbuf = 0;
|
||||
bit_be_bitcount = 0;
|
||||
bit_be_fillbuf(BITBUFSIZ);
|
||||
}
|
||||
|
10
macunpack/bits_be.h
Executable file
10
macunpack/bits_be.h
Executable file
@ -0,0 +1,10 @@
|
||||
#define BITBUFSIZ 16
|
||||
|
||||
extern unsigned int bit_be_bitbuf;
|
||||
extern char *bit_be_filestart;
|
||||
extern int bit_be_inbytes;
|
||||
|
||||
extern void bit_be_fillbuf();
|
||||
extern unsigned int bit_be_getbits();
|
||||
extern void bit_be_init_getbits();
|
||||
|
719
macunpack/cpt.c
Executable file
719
macunpack/cpt.c
Executable file
@ -0,0 +1,719 @@
|
||||
#include "macunpack.h"
|
||||
#ifdef DD
|
||||
#ifndef CPT
|
||||
#define CPT
|
||||
#endif /* CPT */
|
||||
#endif /* DD */
|
||||
#ifdef CPT
|
||||
#include "globals.h"
|
||||
#include "cpt.h"
|
||||
#include "crc.h"
|
||||
#include "../util/util.h"
|
||||
#include "../fileio/machdr.h"
|
||||
#include "../fileio/wrfile.h"
|
||||
#include "../fileio/kind.h"
|
||||
#include "../util/masks.h"
|
||||
#include "huffman.h"
|
||||
|
||||
#define ESC1 0x81
|
||||
#define ESC2 0x82
|
||||
#define NONESEEN 0
|
||||
#define ESC1SEEN 1
|
||||
#define ESC2SEEN 2
|
||||
|
||||
extern char *malloc();
|
||||
extern char *realloc();
|
||||
extern int free();
|
||||
|
||||
static void cpt_uncompact();
|
||||
static unsigned char *cpt_data;
|
||||
static unsigned long cpt_datamax;
|
||||
static unsigned long cpt_datasize;
|
||||
static unsigned char cpt_LZbuff[CIRCSIZE];
|
||||
static unsigned int cpt_LZptr;
|
||||
static unsigned char *cpt_char;
|
||||
static unsigned long cpt_crc;
|
||||
static unsigned long cpt_inlength;
|
||||
static unsigned long cpt_outlength;
|
||||
static int cpt_outstat;
|
||||
static unsigned char cpt_savechar;
|
||||
static unsigned long cpt_newbits;
|
||||
static int cpt_bitsavail;
|
||||
static int cpt_blocksize;
|
||||
/* Lengths is twice the max number of entries, and include slack. */
|
||||
#define SLACK 6
|
||||
static node cpt_Hufftree[512 + SLACK], cpt_LZlength[128 + SLACK],
|
||||
cpt_LZoffs[256 + SLACK];
|
||||
|
||||
static int readcpthdr();
|
||||
static int cpt_filehdr();
|
||||
static void cpt_folder();
|
||||
static void cpt_uncompact();
|
||||
static void cpt_wrfile();
|
||||
void cpt_wrfile1();
|
||||
static void cpt_outch();
|
||||
static void cpt_rle();
|
||||
static void cpt_rle_lzh();
|
||||
static void cpt_readHuff();
|
||||
static int cpt_get6bits();
|
||||
static int cpt_getbit();
|
||||
|
||||
void cpt()
|
||||
{
|
||||
struct cptHdr cpthdr;
|
||||
struct fileHdr filehdr;
|
||||
char *cptindex;
|
||||
int cptindsize;
|
||||
char *cptptr;
|
||||
int i;
|
||||
|
||||
updcrc = zip_updcrc;
|
||||
crcinit = zip_crcinit;
|
||||
cpt_crc = INIT_CRC;
|
||||
if(readcpthdr(&cpthdr) == 0) {
|
||||
(void)fprintf(stderr, "Can't read archive header\n");
|
||||
#ifdef SCAN
|
||||
do_error("macunpack: Can't read archive header");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
|
||||
cptindsize = cpthdr.entries * FILEHDRSIZE;
|
||||
if(cpthdr.commentsize > cptindsize) {
|
||||
cptindsize = cpthdr.commentsize;
|
||||
}
|
||||
cptindex = malloc((unsigned)cptindsize);
|
||||
if(cptindex == NULL) {
|
||||
(void)fprintf(stderr, "Insufficient memory, aborting\n");
|
||||
exit(1);
|
||||
}
|
||||
cptptr = cptindex;
|
||||
if(fread(cptptr, 1, (int)cpthdr.commentsize, infp) != cpthdr.commentsize) {
|
||||
(void)fprintf(stderr, "Can't read comment.\n");
|
||||
#ifdef SCAN
|
||||
do_error("macunpack: Can't read comment");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
cpt_crc = (*updcrc)(cpt_crc, cptptr, cpthdr.commentsize);
|
||||
|
||||
for(i = 0; i < cpthdr.entries; i++) {
|
||||
*cptptr = getc(infp);
|
||||
cpt_crc = (*updcrc)(cpt_crc, cptptr, 1);
|
||||
if(*cptptr & 0x80) {
|
||||
cptptr[F_FOLDER] = 1;
|
||||
*cptptr &= 0x3f;
|
||||
} else {
|
||||
cptptr[F_FOLDER] = 0;
|
||||
}
|
||||
if(fread(cptptr + 1, 1, *cptptr, infp) != *cptptr) {
|
||||
(void)fprintf(stderr, "Can't read file header #%d\n", i+1);
|
||||
#ifdef SCAN
|
||||
do_error("macunpack: Can't read file header");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
cpt_crc = (*updcrc)(cpt_crc, cptptr + 1, *cptptr);
|
||||
if(cptptr[F_FOLDER]) {
|
||||
if(fread(cptptr + F_FOLDERSIZE, 1, 2, infp) != 2) {
|
||||
(void)fprintf(stderr, "Can't read file header #%d\n", i+1);
|
||||
#ifdef SCAN
|
||||
do_error("macunpack: Can't read file header");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
cpt_crc = (*updcrc)(cpt_crc, cptptr + F_FOLDERSIZE, 2);
|
||||
} else {
|
||||
if(fread(cptptr + F_VOLUME, 1, FILEHDRSIZE - F_VOLUME, infp) !=
|
||||
FILEHDRSIZE - F_VOLUME) {
|
||||
(void)fprintf(stderr, "Can't read file header #%d\n", i+1);
|
||||
#ifdef SCAN
|
||||
do_error("macunpack: Can't read file header");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
cpt_crc = (*updcrc)(cpt_crc, cptptr + F_VOLUME,
|
||||
FILEHDRSIZE - F_VOLUME);
|
||||
}
|
||||
cptptr += FILEHDRSIZE;
|
||||
}
|
||||
if(cpt_crc != cpthdr.hdrcrc) {
|
||||
(void)fprintf(stderr, "Header CRC mismatch: got 0x%08x, need 0x%08x\n",
|
||||
(int)cpthdr.hdrcrc, (int)cpt_crc);
|
||||
#ifdef SCAN
|
||||
do_error("macunpack: Header CRC mismatch");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
|
||||
cptptr = cptindex;
|
||||
for(i = 0; i < cpthdr.entries; i++) {
|
||||
if(cpt_filehdr(&filehdr, cptptr) == -1) {
|
||||
(void)fprintf(stderr, "Can't read file header #%d\n", i+1);
|
||||
#ifdef SCAN
|
||||
do_error("macunpack: Can't read file header");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
if(filehdr.folder) {
|
||||
cpt_folder(text, filehdr, cptptr);
|
||||
i += filehdr.foldersize;
|
||||
cptptr += filehdr.foldersize * FILEHDRSIZE;
|
||||
} else {
|
||||
cpt_uncompact(filehdr);
|
||||
}
|
||||
cptptr += FILEHDRSIZE;
|
||||
}
|
||||
(void)free(cptindex);
|
||||
}
|
||||
|
||||
static int readcpthdr(s)
|
||||
struct cptHdr *s;
|
||||
{
|
||||
char temp[CHDRSIZE];
|
||||
|
||||
if(fread(temp, 1, CPTHDRSIZE, infp) != CPTHDRSIZE) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(temp[C_SIGNATURE] != 1) {
|
||||
(void)fprintf(stderr, "Not a Compactor file\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
cpt_datasize = get4(temp + C_IOFFSET);
|
||||
s->offset = cpt_datasize;
|
||||
if(cpt_datasize > cpt_datamax) {
|
||||
if(cpt_datamax == 0) {
|
||||
cpt_data = (unsigned char *)malloc((unsigned)cpt_datasize);
|
||||
} else {
|
||||
cpt_data = (unsigned char *)realloc((char *)cpt_data,
|
||||
(unsigned)cpt_datasize);
|
||||
}
|
||||
cpt_datamax = cpt_datasize;
|
||||
}
|
||||
if(cpt_data == NULL) {
|
||||
(void)fprintf(stderr, "Insufficient memory, aborting\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
if(fread((char *)(cpt_data + CPTHDRSIZE), 1,
|
||||
(int)s->offset - CPTHDRSIZE, infp) != s->offset - CPTHDRSIZE) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(fread(temp + CPTHDRSIZE, 1, CPTHDR2SIZE, infp) != CPTHDR2SIZE) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
cpt_crc = (*updcrc)(cpt_crc, temp + CPTHDRSIZE + C_ENTRIES, 3);
|
||||
s->hdrcrc = get4(temp + CPTHDRSIZE + C_HDRCRC);
|
||||
s->entries = get2(temp + CPTHDRSIZE + C_ENTRIES);
|
||||
s->commentsize = temp[CPTHDRSIZE + C_COMMENT];
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int cpt_filehdr(f, hdr)
|
||||
struct fileHdr *f;
|
||||
char *hdr;
|
||||
{
|
||||
register int i;
|
||||
int n;
|
||||
char ftype[5], fauth[5];
|
||||
|
||||
for(i = 0; i < INFOBYTES; i++) {
|
||||
info[i] = '\0';
|
||||
}
|
||||
|
||||
n = hdr[F_FNAME] & BYTEMASK;
|
||||
if(n > F_NAMELEN) {
|
||||
n = F_NAMELEN;
|
||||
}
|
||||
info[I_NAMEOFF] = n;
|
||||
copy(info + I_NAMEOFF + 1, hdr + F_FNAME + 1, n);
|
||||
transname(hdr + F_FNAME + 1, text, n);
|
||||
|
||||
f->folder = hdr[F_FOLDER];
|
||||
if(f->folder) {
|
||||
f->foldersize = get2(hdr + F_FOLDERSIZE);
|
||||
} else {
|
||||
f->cptFlag = get2(hdr + F_CPTFLAG);
|
||||
f->rsrcLength = get4(hdr + F_RSRCLENGTH);
|
||||
f->dataLength = get4(hdr + F_DATALENGTH);
|
||||
f->compRLength = get4(hdr + F_COMPRLENGTH);
|
||||
f->compDLength = get4(hdr + F_COMPDLENGTH);
|
||||
f->fileCRC = get4(hdr + F_FILECRC);
|
||||
f->FndrFlags = get2(hdr + F_FNDRFLAGS);
|
||||
f->filepos = get4(hdr + F_FILEPOS);
|
||||
f->volume = hdr[F_VOLUME];
|
||||
}
|
||||
|
||||
write_it = 1;
|
||||
if(list) {
|
||||
do_indent(indent);
|
||||
if(f->folder) {
|
||||
(void)fprintf(stderr, "folder=\"%s\"", text);
|
||||
} else {
|
||||
transname(hdr + F_FTYPE, ftype, 4);
|
||||
transname(hdr + F_CREATOR, fauth, 4);
|
||||
(void)fprintf(stderr,
|
||||
"name=\"%s\", type=%4.4s, author=%4.4s, data=%ld, rsrc=%ld",
|
||||
text, ftype, fauth,
|
||||
(long)f->dataLength, (long)f->rsrcLength);
|
||||
}
|
||||
if(info_only) {
|
||||
write_it = 0;
|
||||
}
|
||||
if(query) {
|
||||
write_it = do_query();
|
||||
} else {
|
||||
(void)fputc('\n', stderr);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if(write_it) {
|
||||
define_name(text);
|
||||
|
||||
if(!f->folder) {
|
||||
copy(info + I_TYPEOFF, hdr + F_FTYPE, 4);
|
||||
copy(info + I_AUTHOFF, hdr + F_CREATOR, 4);
|
||||
copy(info + I_FLAGOFF, hdr + F_FNDRFLAGS, 2);
|
||||
copy(info + I_DLENOFF, hdr + F_DATALENGTH, 4);
|
||||
copy(info + I_RLENOFF, hdr + F_RSRCLENGTH, 4);
|
||||
copy(info + I_CTIMOFF, hdr + F_CREATIONDATE, 4);
|
||||
copy(info + I_MTIMOFF, hdr + F_MODDATE, 4);
|
||||
}
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
static void cpt_folder(name, fileh, cptptr)
|
||||
char *name;
|
||||
struct fileHdr fileh;
|
||||
char *cptptr;
|
||||
{
|
||||
int i, nfiles;
|
||||
char loc_name[64];
|
||||
struct fileHdr filehdr;
|
||||
|
||||
for(i = 0; i < 64; i++) {
|
||||
loc_name[i] = name[i];
|
||||
}
|
||||
if(write_it || info_only) {
|
||||
cptptr += FILEHDRSIZE;
|
||||
nfiles = fileh.foldersize;
|
||||
if(write_it) {
|
||||
do_mkdir(text, info);
|
||||
}
|
||||
indent++;
|
||||
for(i = 0; i < nfiles; i++) {
|
||||
if(cpt_filehdr(&filehdr, cptptr) == -1) {
|
||||
(void)fprintf(stderr, "Can't read file header #%d\n", i+1);
|
||||
#ifdef SCAN
|
||||
do_error("macunpack: Can't read file header");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
if(filehdr.folder) {
|
||||
cpt_folder(text, filehdr, cptptr);
|
||||
i += filehdr.foldersize;
|
||||
cptptr += filehdr.foldersize * FILEHDRSIZE;
|
||||
} else {
|
||||
cpt_uncompact(filehdr);
|
||||
}
|
||||
cptptr += FILEHDRSIZE;
|
||||
}
|
||||
if(write_it) {
|
||||
enddir();
|
||||
}
|
||||
indent--;
|
||||
if(list) {
|
||||
do_indent(indent);
|
||||
(void)fprintf(stderr, "leaving folder \"%s\"\n", loc_name);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void cpt_uncompact(filehdr)
|
||||
struct fileHdr filehdr;
|
||||
{
|
||||
if(filehdr.cptFlag & 1) {
|
||||
(void)fprintf(stderr, "\tFile is password protected, skipping file\n");
|
||||
#ifdef SCAN
|
||||
do_idf("", PROTECTED);
|
||||
#endif /* SCAN */
|
||||
return;
|
||||
}
|
||||
if(write_it) {
|
||||
start_info(info, filehdr.rsrcLength, filehdr.dataLength);
|
||||
cpt_crc = INIT_CRC;
|
||||
cpt_char = cpt_data + filehdr.filepos;
|
||||
}
|
||||
if(verbose) {
|
||||
(void)fprintf(stderr, "\tRsrc: ");
|
||||
if(filehdr.compRLength == 0) {
|
||||
(void)fprintf(stderr, "empty");
|
||||
} else if(filehdr.cptFlag & 2) {
|
||||
(void)fprintf(stderr, "RLE/LZH compressed (%4.1f%%)",
|
||||
100.0 * filehdr.compRLength / filehdr.rsrcLength);
|
||||
} else {
|
||||
(void)fprintf(stderr, "RLE compressed (%4.1f%%)",
|
||||
100.0 * filehdr.compRLength / filehdr.rsrcLength);
|
||||
}
|
||||
}
|
||||
if(write_it) {
|
||||
start_rsrc();
|
||||
cpt_wrfile(filehdr.compRLength, filehdr.rsrcLength,
|
||||
filehdr.cptFlag & 2);
|
||||
cpt_char = cpt_data + filehdr.filepos + filehdr.compRLength;
|
||||
}
|
||||
if(verbose) {
|
||||
(void)fprintf(stderr, ", Data: ");
|
||||
if(filehdr.compDLength == 0) {
|
||||
(void)fprintf(stderr, "empty");
|
||||
} else if(filehdr.cptFlag & 4) {
|
||||
(void)fprintf(stderr, "RLE/LZH compressed (%4.1f%%)",
|
||||
100.0 * filehdr.compDLength / filehdr.dataLength);
|
||||
} else {
|
||||
(void)fprintf(stderr, "RLE compressed (%4.1f%%)",
|
||||
100.0 * filehdr.compDLength / filehdr.dataLength);
|
||||
}
|
||||
}
|
||||
if(write_it) {
|
||||
start_data();
|
||||
cpt_wrfile(filehdr.compDLength, filehdr.dataLength,
|
||||
filehdr.cptFlag & 4);
|
||||
if(filehdr.fileCRC != cpt_crc) {
|
||||
(void)fprintf(stderr,
|
||||
"CRC error on file: need 0x%08lx, got 0x%08lx\n",
|
||||
(long)filehdr.fileCRC, (long)cpt_crc);
|
||||
#ifdef SCAN
|
||||
do_error("macunpack: CRC error on file");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
end_file();
|
||||
}
|
||||
if(verbose) {
|
||||
(void)fprintf(stderr, ".\n");
|
||||
}
|
||||
}
|
||||
|
||||
static void cpt_wrfile(ibytes, obytes, type)
|
||||
unsigned long ibytes, obytes;
|
||||
unsigned short type;
|
||||
{
|
||||
if(ibytes == 0) {
|
||||
return;
|
||||
}
|
||||
cpt_outstat = NONESEEN;
|
||||
cpt_inlength = ibytes;
|
||||
cpt_outlength = obytes;
|
||||
cpt_LZptr = 0;
|
||||
cpt_blocksize = 0x1fff0;
|
||||
if(type == 0) {
|
||||
cpt_rle();
|
||||
} else {
|
||||
cpt_rle_lzh();
|
||||
}
|
||||
cpt_crc = (*updcrc)(cpt_crc, out_buffer, obytes);
|
||||
}
|
||||
|
||||
void cpt_wrfile1(in_char, ibytes, obytes, type, blocksize)
|
||||
unsigned char *in_char;
|
||||
unsigned long ibytes, obytes, blocksize;
|
||||
int type;
|
||||
{
|
||||
cpt_char = in_char;
|
||||
if(ibytes == 0) {
|
||||
return;
|
||||
}
|
||||
cpt_outstat = NONESEEN;
|
||||
cpt_inlength = ibytes;
|
||||
cpt_outlength = obytes;
|
||||
cpt_LZptr = 0;
|
||||
cpt_blocksize = blocksize;
|
||||
if(type == 0) {
|
||||
cpt_rle();
|
||||
} else {
|
||||
cpt_rle_lzh();
|
||||
}
|
||||
}
|
||||
|
||||
static void cpt_outch(ch)
|
||||
unsigned char ch;
|
||||
{
|
||||
cpt_LZbuff[cpt_LZptr++ & (CIRCSIZE - 1)] = ch;
|
||||
switch(cpt_outstat) {
|
||||
case NONESEEN:
|
||||
if(ch == ESC1 && cpt_outlength != 1) {
|
||||
cpt_outstat = ESC1SEEN;
|
||||
} else {
|
||||
cpt_savechar = ch;
|
||||
*out_ptr++ = ch;
|
||||
cpt_outlength--;
|
||||
}
|
||||
break;
|
||||
case ESC1SEEN:
|
||||
if(ch == ESC2) {
|
||||
cpt_outstat = ESC2SEEN;
|
||||
} else {
|
||||
cpt_savechar = ESC1;
|
||||
*out_ptr++ = ESC1;
|
||||
cpt_outlength--;
|
||||
if(cpt_outlength == 0) {
|
||||
return;
|
||||
}
|
||||
if(ch == ESC1 && cpt_outlength != 1) {
|
||||
return;
|
||||
}
|
||||
cpt_outstat = NONESEEN;
|
||||
cpt_savechar = ch;
|
||||
*out_ptr++ = ch;
|
||||
cpt_outlength--;
|
||||
}
|
||||
break;
|
||||
case ESC2SEEN:
|
||||
cpt_outstat = NONESEEN;
|
||||
if(ch != 0) {
|
||||
while(--ch != 0) {
|
||||
*out_ptr++ = cpt_savechar;
|
||||
cpt_outlength--;
|
||||
if(cpt_outlength == 0) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
*out_ptr++ = ESC1;
|
||||
cpt_outlength--;
|
||||
if(cpt_outlength == 0) {
|
||||
return;
|
||||
}
|
||||
cpt_savechar = ESC2;
|
||||
*out_ptr++ = cpt_savechar;
|
||||
cpt_outlength--;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------------------------*/
|
||||
/* Run length encoding */
|
||||
/*---------------------------------------------------------------------------*/
|
||||
static void cpt_rle()
|
||||
{
|
||||
while(cpt_inlength-- > 0) {
|
||||
cpt_outch(*cpt_char++);
|
||||
}
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------------------------*/
|
||||
/* Run length encoding plus LZ compression plus Huffman encoding */
|
||||
/*---------------------------------------------------------------------------*/
|
||||
static void cpt_rle_lzh()
|
||||
{
|
||||
int block_count;
|
||||
unsigned int bptr;
|
||||
int Huffchar, LZlength, LZoffs;
|
||||
|
||||
get_bit = cpt_getbit;
|
||||
cpt_LZbuff[CIRCSIZE - 3] = 0;
|
||||
cpt_LZbuff[CIRCSIZE - 2] = 0;
|
||||
cpt_LZbuff[CIRCSIZE - 1] = 0;
|
||||
cpt_LZptr = 0;
|
||||
while(cpt_outlength != 0) {
|
||||
cpt_readHuff(256, cpt_Hufftree);
|
||||
cpt_readHuff(64, cpt_LZlength);
|
||||
cpt_readHuff(128, cpt_LZoffs);
|
||||
block_count = 0;
|
||||
cpt_newbits = (*cpt_char++ << 8);
|
||||
cpt_newbits = cpt_newbits | *cpt_char++;
|
||||
cpt_newbits = cpt_newbits << 16;
|
||||
cpt_bitsavail = 16;
|
||||
while(block_count < cpt_blocksize && cpt_outlength != 0) {
|
||||
if(cpt_getbit()) {
|
||||
Huffchar = gethuffbyte(cpt_Hufftree);
|
||||
cpt_outch((unsigned char)Huffchar);
|
||||
block_count += 2;
|
||||
} else {
|
||||
LZlength = gethuffbyte(cpt_LZlength);
|
||||
LZoffs = gethuffbyte(cpt_LZoffs);
|
||||
LZoffs = (LZoffs << 6) | cpt_get6bits();
|
||||
bptr = cpt_LZptr - LZoffs;
|
||||
while(LZlength-- > 0) {
|
||||
cpt_outch(cpt_LZbuff[bptr++ & (CIRCSIZE - 1)]);
|
||||
}
|
||||
block_count += 3;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Based on unimplod from unzip; difference are noted below. */
|
||||
typedef struct sf_entry {
|
||||
int Value;
|
||||
int BitLength;
|
||||
} sf_entry;
|
||||
|
||||
/* See routine LoadTree. The parameter tree (actually an array and
|
||||
two integers) are only used locally in this version and hence locally
|
||||
declared. The parameter nodes has been renamed Hufftree.... */
|
||||
static void cpt_readHuff(size, Hufftree)
|
||||
int size;
|
||||
struct node *Hufftree;
|
||||
{
|
||||
sf_entry tree_entry[256 + SLACK]; /* maximal number of elements */
|
||||
int tree_entries;
|
||||
int tree_MaxLength; /* finishes local declaration of tree */
|
||||
|
||||
int treeBytes, i, len; /* declarations from ReadLengths */
|
||||
|
||||
/* declarations from SortLengths */
|
||||
sf_entry *ejm1;
|
||||
int j;
|
||||
sf_entry *entry;
|
||||
/* int i already above */
|
||||
sf_entry tmp;
|
||||
int entries;
|
||||
unsigned a, b;
|
||||
|
||||
/* declarations from GenerateTrees */
|
||||
int codelen, lvlstart, next, parents;
|
||||
/* int i, j already above */
|
||||
|
||||
/* for Compactor */
|
||||
int tree_count[32];
|
||||
/* end declarations */
|
||||
|
||||
/* next paraphrased from ReadLengths with adaption for Compactor. */
|
||||
treeBytes = *cpt_char++;
|
||||
if(size < treeBytes * 2) { /* too many entries, something is wrong! */
|
||||
(void)fprintf(stderr, "Bytes is: %d, expected: %d\n", treeBytes,
|
||||
size / 2);
|
||||
#ifdef SCAN
|
||||
do_error("macunpack: error in coding tree");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
for(i = 0; i < 32; i++) {
|
||||
tree_count[i] = 0;
|
||||
}
|
||||
i = 0;
|
||||
tree_MaxLength = 0;
|
||||
tree_entries = 0;
|
||||
while(treeBytes-- > 0) { /* adaption for Compactor */
|
||||
len = (*cpt_char) >> 4;
|
||||
if(len != 0) { /* only if length unequal zero */
|
||||
if(len > tree_MaxLength) {
|
||||
tree_MaxLength = len;
|
||||
}
|
||||
tree_count[len]++;
|
||||
tree_entry[tree_entries].Value = i;
|
||||
tree_entry[tree_entries++].BitLength = len;
|
||||
}
|
||||
i++;
|
||||
len = *cpt_char++ & NIBBLEMASK;
|
||||
if(len != 0) { /* only if length unequal zero */
|
||||
if(len > tree_MaxLength) {
|
||||
tree_MaxLength = len;
|
||||
}
|
||||
tree_count[len]++;
|
||||
tree_entry[tree_entries].Value = i;
|
||||
tree_entry[tree_entries++].BitLength = len;
|
||||
}
|
||||
i++;
|
||||
}
|
||||
|
||||
/* Compactor allows unused trailing codes in its Huffman tree! */
|
||||
j = 0;
|
||||
for(i = 0; i <= tree_MaxLength; i++) {
|
||||
j = (j << 1) + tree_count[i];
|
||||
}
|
||||
j = (1 <<tree_MaxLength) - j;
|
||||
/* Insert the unused entries for sorting purposes. */
|
||||
for(i = 0; i < j; i++) {
|
||||
tree_entry[tree_entries].Value = size;
|
||||
tree_entry[tree_entries++].BitLength = tree_MaxLength;
|
||||
}
|
||||
|
||||
/* adaption from SortLengths */
|
||||
entry = &(tree_entry[0]);
|
||||
entries = tree_entries;
|
||||
for(i = 0; ++i < entries;) {
|
||||
tmp = entry[i];
|
||||
b = tmp.BitLength;
|
||||
j = i;
|
||||
while((j > 0) && ((a = (ejm1 = &(entry[j - 1]))->BitLength) >= b)) {
|
||||
if((a == b) && (ejm1->Value <= tmp.Value)) {
|
||||
break;
|
||||
}
|
||||
*(ejm1 + 1) = *ejm1;
|
||||
--j;
|
||||
}
|
||||
entry[j] = tmp;
|
||||
}
|
||||
|
||||
/* Adapted from GenerateTrees */
|
||||
i = tree_entries - 1;
|
||||
/* starting at the upper end (and reversing loop) because of Compactor */
|
||||
lvlstart = next = size * 2 + SLACK - 1;
|
||||
/* slight adaption because of different node format used */
|
||||
for(codelen = tree_MaxLength; codelen >= 1; --codelen) {
|
||||
while((i >= 0) && (tree_entry[i].BitLength == codelen)) {
|
||||
Hufftree[next].byte = tree_entry[i].Value;
|
||||
Hufftree[next].flag = 1;
|
||||
next--;
|
||||
i--;
|
||||
}
|
||||
parents = next;
|
||||
if(codelen > 1) {
|
||||
/* reversed loop */
|
||||
for(j = lvlstart; j > parents + 1; j-= 2) {
|
||||
Hufftree[next].one = &(Hufftree[j]);
|
||||
Hufftree[next].zero = &(Hufftree[j - 1]);
|
||||
Hufftree[next].flag = 0;
|
||||
next--;
|
||||
}
|
||||
}
|
||||
lvlstart = parents;
|
||||
}
|
||||
Hufftree[0].one = &(Hufftree[next + 2]);
|
||||
Hufftree[0].zero = &(Hufftree[next + 1]);
|
||||
Hufftree[0].flag = 0;
|
||||
}
|
||||
|
||||
static int cpt_get6bits()
|
||||
{
|
||||
int b = 0, cn;
|
||||
|
||||
b = (cpt_newbits >> 26) & 0x3f;
|
||||
cpt_bitsavail -= 6;
|
||||
cpt_newbits <<= 6;
|
||||
if(cpt_bitsavail < 16) {
|
||||
cn = (*cpt_char++ << 8);
|
||||
cn |= *cpt_char++;
|
||||
cpt_newbits |= (cn << (16 - cpt_bitsavail));
|
||||
cpt_bitsavail += 16;
|
||||
}
|
||||
return b;
|
||||
}
|
||||
|
||||
static int cpt_getbit()
|
||||
{
|
||||
int b;
|
||||
|
||||
b = (cpt_newbits >> 31) & 1;
|
||||
cpt_bitsavail--;
|
||||
if(cpt_bitsavail < 16) {
|
||||
cpt_newbits |= (*cpt_char++ << 8);
|
||||
cpt_newbits |= *cpt_char++;
|
||||
cpt_bitsavail += 16;
|
||||
}
|
||||
cpt_newbits <<= 1;
|
||||
return b;
|
||||
}
|
||||
#else /* CPT */
|
||||
int cpt; /* keep lint and some compilers happy */
|
||||
#endif /* CPT */
|
||||
|
93
macunpack/cpt.h
Executable file
93
macunpack/cpt.h
Executable file
@ -0,0 +1,93 @@
|
||||
#define C_SIGNATURE 0
|
||||
#define C_VOLUME 1
|
||||
#define C_XMAGIC 2
|
||||
#define C_IOFFSET 4
|
||||
#define CPTHDRSIZE 8
|
||||
|
||||
#define C_HDRCRC 0
|
||||
#define C_ENTRIES 4
|
||||
#define C_COMMENT 6
|
||||
#define CPTHDR2SIZE 7
|
||||
|
||||
#define CHDRSIZE (CPTHDRSIZE+CPTHDR2SIZE)
|
||||
|
||||
#define F_FNAME 0
|
||||
#define F_FOLDER 32
|
||||
#define F_FOLDERSIZE 33
|
||||
#define F_VOLUME 35
|
||||
#define F_FILEPOS 36
|
||||
#define F_FTYPE 40
|
||||
#define F_CREATOR 44
|
||||
#define F_CREATIONDATE 48
|
||||
#define F_MODDATE 52
|
||||
#define F_FNDRFLAGS 56
|
||||
#define F_FILECRC 58
|
||||
#define F_CPTFLAG 62
|
||||
#define F_RSRCLENGTH 64
|
||||
#define F_DATALENGTH 68
|
||||
#define F_COMPRLENGTH 72
|
||||
#define F_COMPDLENGTH 76
|
||||
#define FILEHDRSIZE 80
|
||||
|
||||
typedef long OSType;
|
||||
|
||||
typedef struct cptHdr { /* 8 bytes */
|
||||
unsigned char signature; /* = 1 -- for verification */
|
||||
unsigned char volume; /* for multi-file archives */
|
||||
unsigned short xmagic; /* verification multi-file consistency*/
|
||||
unsigned long offset; /* index offset */
|
||||
/* The following are really in header2 at offset */
|
||||
unsigned long hdrcrc; /* header crc */
|
||||
unsigned short entries; /* number of index entries */
|
||||
unsigned char commentsize; /* number of bytes comment that follow*/
|
||||
};
|
||||
|
||||
typedef struct fileHdr { /* 78 bytes */
|
||||
unsigned char fName[32]; /* a STR32 */
|
||||
unsigned char folder; /* set to 1 if a folder */
|
||||
unsigned short foldersize; /* number of entries in folder */
|
||||
unsigned char volume; /* for multi-file archives */
|
||||
unsigned long filepos; /* position of data in file */
|
||||
OSType fType; /* file type */
|
||||
OSType fCreator; /* er... */
|
||||
unsigned long creationDate;
|
||||
unsigned long modDate; /* !restored-compat w/backup prgms */
|
||||
unsigned short FndrFlags; /* copy of Finder flags. For our
|
||||
purposes, we can clear:
|
||||
busy,onDesk */
|
||||
unsigned long fileCRC; /* crc on file */
|
||||
unsigned short cptFlag; /* cpt flags */
|
||||
unsigned long rsrcLength; /* decompressed lengths */
|
||||
unsigned long dataLength;
|
||||
unsigned long compRLength; /* compressed lengths */
|
||||
unsigned long compDLength;
|
||||
};
|
||||
|
||||
|
||||
/* file format is:
|
||||
cptArchiveHdr
|
||||
file1data
|
||||
file1RsrcFork
|
||||
file1DataFork
|
||||
file2data
|
||||
file2RsrcFork
|
||||
file2DataFork
|
||||
.
|
||||
.
|
||||
.
|
||||
fileNdata
|
||||
fileNRsrcFork
|
||||
fileNDataFork
|
||||
cptIndex
|
||||
*/
|
||||
|
||||
|
||||
|
||||
/* cpt flags */
|
||||
#define encryp 1 /* file is encrypted */
|
||||
#define crsrc 2 /* resource fork is compressed */
|
||||
#define cdata 4 /* data fork is compressed */
|
||||
/* ???? 8 /* unknown */
|
||||
|
||||
#define CIRCSIZE 8192
|
||||
|
BIN
macunpack/cpt.o
Normal file
BIN
macunpack/cpt.o
Normal file
Binary file not shown.
4
macunpack/crc.c
Executable file
4
macunpack/crc.c
Executable file
@ -0,0 +1,4 @@
|
||||
unsigned long crcinit;
|
||||
|
||||
unsigned long (*updcrc)();
|
||||
|
13
macunpack/crc.h
Executable file
13
macunpack/crc.h
Executable file
@ -0,0 +1,13 @@
|
||||
#define INIT_CRC crcinit
|
||||
|
||||
extern unsigned long arc_crcinit;
|
||||
extern unsigned long binhex_crcinit;
|
||||
extern unsigned long zip_crcinit;
|
||||
|
||||
extern unsigned long arc_updcrc();
|
||||
extern unsigned long binhex_updcrc();
|
||||
extern unsigned long zip_updcrc();
|
||||
|
||||
extern unsigned long crcinit;
|
||||
extern unsigned long (*updcrc)();
|
||||
|
1042
macunpack/dd.c
Executable file
1042
macunpack/dd.c
Executable file
File diff suppressed because it is too large
Load Diff
125
macunpack/dd.h
Executable file
125
macunpack/dd.h
Executable file
@ -0,0 +1,125 @@
|
||||
#define MAGIC1 "DDAR"
|
||||
#define MAGIC2 "\253\315\000\124"
|
||||
|
||||
/* Initial header */
|
||||
#define ARCHHDRCRC 76
|
||||
#define ARCHHDRSIZE 78
|
||||
|
||||
/* File headers */
|
||||
#define D_MAGIC 0
|
||||
#define D_FILL1 4
|
||||
#define D_FNAME 8
|
||||
#define D_ISDIR 72
|
||||
#define D_ENDDIR 73
|
||||
#define D_DATALENGTH 74
|
||||
#define D_RSRCLENGTH 78
|
||||
#define D_CTIME 82
|
||||
#define D_MTIME 86
|
||||
#define D_FTYPE 90
|
||||
#define D_CREATOR 94
|
||||
#define D_FNDRFLAGS 98
|
||||
#define D_FILL2 100
|
||||
#define D_DATACRC 118
|
||||
#define D_RSRCCRC 120
|
||||
#define D_HDRCRC 122
|
||||
#define FILEHDRSIZE 124
|
||||
|
||||
/* Compressed file header */
|
||||
#define C_MAGIC 0
|
||||
#define C_DATALENGTH 4
|
||||
#define C_DATACLENGTH 8
|
||||
#define C_RSRCLENGTH 12
|
||||
#define C_RSRCCLENGTH 16
|
||||
#define C_DATAMETHOD 20
|
||||
#define C_RSRCMETHOD 21
|
||||
#define C_INFO1 22
|
||||
#define C_MTIME 24
|
||||
#define C_CTIME 28
|
||||
#define C_FTYPE 32
|
||||
#define C_CREATOR 36
|
||||
#define C_FNDRFLAGS 40
|
||||
#define C_FILL1 42
|
||||
#define C_DATACRC 48
|
||||
#define C_RSRCCRC 50
|
||||
#define C_INFO2 52
|
||||
#define C_DATAINFO 54
|
||||
#define C_RSRCINFO 56
|
||||
#define C_FILL2 58
|
||||
#define C_DATACRC2 78
|
||||
#define C_RSRCCRC2 80
|
||||
#define C_HDRCRC 82
|
||||
#define CFILEHDRSIZE 84
|
||||
|
||||
typedef long OSType;
|
||||
|
||||
typedef struct fileHdr { /* 124 bytes */
|
||||
unsigned char magic[4]; /* "DDAR" */
|
||||
unsigned char fill1[4]; /* ??? */
|
||||
unsigned char fName[64]; /* a STR63 */
|
||||
unsigned char isdir; /* starts a directory? */
|
||||
unsigned char enddir; /* terminates a directory? */
|
||||
unsigned long dataLength; /* lengths */
|
||||
unsigned long rsrcLength;
|
||||
unsigned long creationDate;
|
||||
unsigned long modDate;
|
||||
OSType fType; /* file type */
|
||||
OSType fCreator; /* er... */
|
||||
unsigned short FndrFlags; /* copy of Finder flags. For our
|
||||
purposes, we can clear:
|
||||
busy,onDesk */
|
||||
unsigned char fill2[18]; /* ??? */
|
||||
unsigned short datacrc; /* checksum */
|
||||
unsigned short rsrccrc;
|
||||
unsigned short hdrcrc; /* true crc */
|
||||
};
|
||||
|
||||
typedef struct fileCHdr { /* 84 bytes */
|
||||
unsigned char magic[4]; /* "\253\315\000\124" */
|
||||
unsigned long dataLength; /* lengths */
|
||||
unsigned long dataCLength;
|
||||
unsigned long rsrcLength;
|
||||
unsigned long rsrcCLength;
|
||||
unsigned char datamethod; /* compression method used */
|
||||
unsigned char rsrcmethod;
|
||||
unsigned char info1; /* flags ??? */
|
||||
unsigned char fill3;
|
||||
unsigned long modDate;
|
||||
unsigned long creationDate;
|
||||
OSType fType; /* file type */
|
||||
OSType fCreator; /* er... */
|
||||
unsigned short FndrFlags; /* copy of Finder flags. For our
|
||||
purposes, we can clear:
|
||||
busy,onDesk */
|
||||
unsigned char fill1[6]; /* ??? */
|
||||
unsigned short datacrc; /* checksum */
|
||||
unsigned short rsrccrc;
|
||||
unsigned char info2; /* flags ??? */
|
||||
unsigned char fill4;
|
||||
unsigned short datainfo; /* ??? */
|
||||
unsigned short rsrcinfo; /* ??? */
|
||||
unsigned char fill2[20]; /* ??? */
|
||||
unsigned short datacrc2; /* other checksum */
|
||||
unsigned short rsrccrc2;
|
||||
unsigned short hdrcrc; /* true crc */
|
||||
};
|
||||
|
||||
#define DD_FILE 0
|
||||
#define DD_COPY 1
|
||||
#define DD_SDIR 2
|
||||
#define DD_EDIR 3
|
||||
#define DD_IVAL 4
|
||||
|
||||
/* Methods used */
|
||||
#define nocomp 0
|
||||
#define lzc 1
|
||||
#define method2 2
|
||||
#define rle 3
|
||||
#define huffman 4
|
||||
#define method5 5
|
||||
#define method6 6
|
||||
#define lzss 7
|
||||
#define cpt_compat 8
|
||||
#define method9 9
|
||||
|
||||
#define ESC 0x144 /* Repeat packing escape */
|
||||
|
225
macunpack/de_compress.c
Executable file
225
macunpack/de_compress.c
Executable file
@ -0,0 +1,225 @@
|
||||
#include "macunpack.h"
|
||||
#ifdef SIT
|
||||
#define DECOMPRESS
|
||||
#endif /* SIT */
|
||||
#ifdef LZC
|
||||
#define DECOMPRESS
|
||||
#endif /* LZC */
|
||||
#ifdef DECOMPRESS
|
||||
#include "globals.h"
|
||||
#include "../fileio/wrfile.h"
|
||||
|
||||
/* Written to allow for bits to be upto 16, MacCompress can use 16 bits */
|
||||
|
||||
#define BITS 16
|
||||
#define HSIZE 69001 /* 95% occupancy */
|
||||
|
||||
#define INIT_BITS 9 /* initial number of bits/code */
|
||||
|
||||
static int n_bits; /* number of bits/code */
|
||||
static int maxbits; /* user settable max # bits/code */
|
||||
static long maxcode; /* maximum code, given n_bits */
|
||||
static long maxmaxcode; /* should NEVER generate this code */
|
||||
# define MAXCODE(n_bits) ((1 << (n_bits)) - 1)
|
||||
|
||||
static long htab [HSIZE];
|
||||
static unsigned short codetab [HSIZE];
|
||||
|
||||
#define tab_prefixof(i) codetab[i]
|
||||
#define tab_suffixof(i) ((unsigned char *)(htab))[i]
|
||||
#define de_stack ((unsigned char *)&tab_suffixof(1<<BITS))
|
||||
|
||||
static long free_ent = 0; /* first unused entry */
|
||||
|
||||
static long getcode();
|
||||
|
||||
static int clear_flg = 0;
|
||||
|
||||
/*
|
||||
* the next two codes should not be changed lightly, as they must not
|
||||
* lie within the contiguous general code space.
|
||||
*/
|
||||
#define FIRST 257 /* first free entry */
|
||||
#define CLEAR 256 /* table clear output code */
|
||||
|
||||
static int toread;
|
||||
|
||||
void de_compress(ibytes, mb)
|
||||
unsigned long ibytes;
|
||||
int mb;
|
||||
{
|
||||
register unsigned char *stackp;
|
||||
register int finchar;
|
||||
register long code, oldcode, incode;
|
||||
|
||||
toread = ibytes;
|
||||
maxbits = mb;
|
||||
maxmaxcode = 1 << maxbits;
|
||||
maxcode = MAXCODE(n_bits = INIT_BITS);
|
||||
for(code = 255; code >= 0; code--) {
|
||||
tab_prefixof(code) = 0;
|
||||
tab_suffixof(code) = (unsigned char)code;
|
||||
}
|
||||
free_ent = FIRST;
|
||||
finchar = oldcode = getcode();
|
||||
if(oldcode == -1) { /* EOF already? */
|
||||
return; /* Get out of here */
|
||||
}
|
||||
/* first code must be 8 bits = char */
|
||||
*out_ptr++ = (char)finchar;
|
||||
stackp = de_stack;
|
||||
while((code = getcode()) > -1) {
|
||||
if(code == CLEAR) {
|
||||
for(code = 255; code >= 0; code--) {
|
||||
tab_prefixof(code) = 0;
|
||||
}
|
||||
clear_flg = 1;
|
||||
free_ent = FIRST - 1;
|
||||
if((code = getcode()) == -1) { /* O, untimely death! */
|
||||
break;
|
||||
}
|
||||
}
|
||||
incode = code;
|
||||
/*
|
||||
* Special case for KwKwK string.
|
||||
*/
|
||||
if(code >= free_ent) {
|
||||
*stackp++ = finchar;
|
||||
code = oldcode;
|
||||
}
|
||||
/*
|
||||
* Generate output characters in reverse order
|
||||
*/
|
||||
while(code >= 256) {
|
||||
*stackp++ = tab_suffixof(code);
|
||||
code = tab_prefixof(code);
|
||||
}
|
||||
*stackp++ = finchar = tab_suffixof(code);
|
||||
/*
|
||||
* And put them out in forward order
|
||||
*/
|
||||
do {
|
||||
*out_ptr++ = (char)*--stackp;
|
||||
} while(stackp > de_stack);
|
||||
/*
|
||||
* Generate the new entry.
|
||||
*/
|
||||
if((code=free_ent) < maxmaxcode) {
|
||||
tab_prefixof(code) = (unsigned short)oldcode;
|
||||
tab_suffixof(code) = finchar;
|
||||
free_ent = code+1;
|
||||
}
|
||||
/*
|
||||
* Remember previous code.
|
||||
*/
|
||||
oldcode = incode;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
static unsigned char rmask[9] =
|
||||
{0x00, 0x01, 0x03, 0x07, 0x0f, 0x1f, 0x3f, 0x7f, 0xff};
|
||||
|
||||
static int get_core_bytes;
|
||||
static char *core_ptr;
|
||||
static int file_bytes();
|
||||
static int core_bytes();
|
||||
|
||||
static long getcode()
|
||||
{
|
||||
register long code;
|
||||
static int offset = 0, size = 0;
|
||||
static unsigned char buf[BITS];
|
||||
register int r_off, bits;
|
||||
register unsigned char *bp = buf;
|
||||
|
||||
if(clear_flg > 0 || offset >= size || free_ent > maxcode) {
|
||||
/*
|
||||
* If the next entry will be too big for the current code
|
||||
* size, then we must increase the size. This implies reading
|
||||
* a new buffer full, too.
|
||||
*/
|
||||
if(free_ent > maxcode) {
|
||||
n_bits++;
|
||||
if(n_bits == maxbits) {
|
||||
maxcode = maxmaxcode; /* won't get any bigger now */
|
||||
} else {
|
||||
maxcode = MAXCODE(n_bits);
|
||||
}
|
||||
}
|
||||
if(clear_flg > 0) {
|
||||
maxcode = MAXCODE (n_bits = INIT_BITS);
|
||||
clear_flg = 0;
|
||||
}
|
||||
if(toread == 0) {
|
||||
return -1;
|
||||
}
|
||||
if(get_core_bytes) {
|
||||
size = core_bytes((char *)buf, (n_bits < toread ? n_bits : toread));
|
||||
} else {
|
||||
size = file_bytes((char *)buf, (n_bits < toread ? n_bits : toread));
|
||||
}
|
||||
toread -= size;
|
||||
if(size <= 0) {
|
||||
(void)fprintf(stderr, "Premature EOF\n");
|
||||
#ifdef SCAN
|
||||
do_error("macunpack: Premature EOF");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
offset = 0;
|
||||
/* Round size down to integral number of codes */
|
||||
size = (size << 3) - (n_bits - 1);
|
||||
}
|
||||
r_off = offset;
|
||||
bits = n_bits;
|
||||
/*
|
||||
* Get to the first byte.
|
||||
*/
|
||||
bp += (r_off >> 3);
|
||||
r_off &= 7;
|
||||
/* Get first part (low order bits) */
|
||||
code = (*bp++ >> r_off);
|
||||
bits -= (8 - r_off);
|
||||
r_off = 8 - r_off; /* now, offset into code word */
|
||||
/* Get any 8 bit parts in the middle (<=1 for up to 16 bits). */
|
||||
if(bits >= 8) {
|
||||
code |= *bp++ << r_off;
|
||||
r_off += 8;
|
||||
bits -= 8;
|
||||
}
|
||||
/* high order bits. */
|
||||
code |= (*bp & rmask[bits]) << r_off;
|
||||
offset += n_bits;
|
||||
return code;
|
||||
}
|
||||
|
||||
static int file_bytes(buf, length)
|
||||
char *buf;
|
||||
int length;
|
||||
{
|
||||
return fread(buf, 1, length, infp);
|
||||
}
|
||||
|
||||
static int core_bytes(buf, length)
|
||||
char *buf;
|
||||
int length;
|
||||
{
|
||||
int i;
|
||||
|
||||
for(i = 0; i < length; i++) {
|
||||
*buf++ = *core_ptr++;
|
||||
}
|
||||
return length;
|
||||
}
|
||||
|
||||
void core_compress(ptr)
|
||||
char *ptr;
|
||||
{
|
||||
core_ptr = ptr;
|
||||
get_core_bytes = ptr != NULL;
|
||||
}
|
||||
#else /* DECOMPRESS */
|
||||
int decompress; /* keep lint and some compilers happy */
|
||||
#endif /* DECOMPRESS */
|
||||
|
154
macunpack/de_huffman.c
Executable file
154
macunpack/de_huffman.c
Executable file
@ -0,0 +1,154 @@
|
||||
#include "macunpack.h"
|
||||
#ifdef JDW
|
||||
#define DEHUFFMAN
|
||||
#endif /* JDW */
|
||||
#ifdef STF
|
||||
#define DEHUFFMAN
|
||||
#endif /* STF */
|
||||
#ifdef PIT
|
||||
#define DEHUFFMAN
|
||||
#endif /* PIT */
|
||||
#ifdef SIT
|
||||
#define DEHUFFMAN
|
||||
#endif /* SIT */
|
||||
#ifdef CPT
|
||||
#define DEHUFFMAN
|
||||
#endif /* CPT */
|
||||
#ifdef DEHUFFMAN
|
||||
#include "globals.h"
|
||||
#include "../util/masks.h"
|
||||
#include "../fileio/wrfile.h"
|
||||
#include "huffman.h"
|
||||
#include "../util/util.h"
|
||||
|
||||
int (*get_bit)();
|
||||
int bytesread;
|
||||
/* 515 because StuffIt Classic needs more than the needed 511 */
|
||||
struct node nodelist[515];
|
||||
static int getbit_be();
|
||||
static int getbit_le();
|
||||
static int getdecodebyte();
|
||||
|
||||
static node *nodeptr, *read_sub_tree();
|
||||
|
||||
static int bit;
|
||||
|
||||
void de_huffman(obytes)
|
||||
unsigned long obytes;
|
||||
{
|
||||
while(obytes != 0) {
|
||||
*out_ptr++ = gethuffbyte(nodelist);
|
||||
obytes--;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
void de_huffman_end(term)
|
||||
unsigned int term;
|
||||
{
|
||||
int c;
|
||||
|
||||
while((c = gethuffbyte(nodelist)) != term) {
|
||||
*out_ptr++ = c;
|
||||
}
|
||||
}
|
||||
|
||||
void set_huffman(endian)
|
||||
int endian;
|
||||
{
|
||||
if(endian == HUFF_LE) {
|
||||
get_bit = getbit_le;
|
||||
} else if(endian == HUFF_BE) {
|
||||
get_bit = getbit_be;
|
||||
}
|
||||
}
|
||||
|
||||
void read_tree()
|
||||
{
|
||||
nodeptr = nodelist;
|
||||
bit = 0; /* put us on a boundary */
|
||||
(void)read_sub_tree();
|
||||
}
|
||||
|
||||
/* This routine recursively reads the Huffman encoding table and builds
|
||||
a decoding tree. */
|
||||
static node *read_sub_tree()
|
||||
{
|
||||
node *np;
|
||||
|
||||
np = nodeptr++;
|
||||
if((*get_bit)() == 1) {
|
||||
np->flag = 1;
|
||||
np->byte = getdecodebyte();
|
||||
} else {
|
||||
np->flag = 0;
|
||||
np->zero = read_sub_tree();
|
||||
np->one = read_sub_tree();
|
||||
}
|
||||
return np;
|
||||
}
|
||||
|
||||
/* This routine returns the next bit in the input stream (MSB first) */
|
||||
static int getbit_be()
|
||||
{
|
||||
static int b;
|
||||
|
||||
if(bit == 0) {
|
||||
b = getb(infp) & BYTEMASK;
|
||||
bit = 8;
|
||||
bytesread++;
|
||||
}
|
||||
bit--;
|
||||
return (b >> bit) & 1;
|
||||
}
|
||||
|
||||
/* This routine returns the next bit in the input stream (LSB first) */
|
||||
static int getbit_le()
|
||||
{
|
||||
static int b;
|
||||
|
||||
if(bit == 0) {
|
||||
b = getb(infp) & BYTEMASK;
|
||||
bit = 8;
|
||||
bytesread++;
|
||||
}
|
||||
bit--;
|
||||
return (b >> (7 - bit)) & 1;
|
||||
}
|
||||
|
||||
void clrhuff()
|
||||
{
|
||||
bit = 0;
|
||||
}
|
||||
|
||||
int gethuffbyte(l_nodelist)
|
||||
node *l_nodelist;
|
||||
{
|
||||
register node *np;
|
||||
|
||||
np = l_nodelist;
|
||||
while(np->flag == 0) {
|
||||
np = (*get_bit)() ? np->one : np->zero;
|
||||
}
|
||||
return np->byte;
|
||||
}
|
||||
|
||||
int getihuffbyte()
|
||||
{
|
||||
return gethuffbyte(nodelist);
|
||||
}
|
||||
|
||||
static int getdecodebyte()
|
||||
{
|
||||
register int i, b;
|
||||
|
||||
b = 0;
|
||||
for(i = 8; i > 0; i--) {
|
||||
b = (b << 1) + (*get_bit)();
|
||||
}
|
||||
return b;
|
||||
}
|
||||
#else /* DEHUFFMAN */
|
||||
int dehuffman; /* keep lint and some compilers happy */
|
||||
#endif /* DEHUFFMAN */
|
||||
|
276
macunpack/de_lzah.c
Executable file
276
macunpack/de_lzah.c
Executable file
@ -0,0 +1,276 @@
|
||||
#include "macunpack.h"
|
||||
#ifdef SIT
|
||||
#define DELZAH
|
||||
#endif /* SIT */
|
||||
#ifdef LZH
|
||||
#define DELZAH
|
||||
#endif /* LZH */
|
||||
#ifdef DELZAH
|
||||
#include "globals.h"
|
||||
#include "../util/masks.h"
|
||||
#include "../fileio/wrfile.h"
|
||||
|
||||
/* Note: compare with LZSS decoding in lharc! */
|
||||
|
||||
#define N 314
|
||||
#define T (2*N-1)
|
||||
|
||||
/* Huffman table used for first 6 bits of offset:
|
||||
#bits codes
|
||||
3 0x000
|
||||
4 0x040-0x080
|
||||
5 0x100-0x2c0
|
||||
6 0x300-0x5c0
|
||||
7 0x600-0xbc0
|
||||
8 0xc00-0xfc0
|
||||
*/
|
||||
|
||||
static unsigned short HuffCode[] = {
|
||||
0x000, 0x000, 0x000, 0x000, 0x000, 0x000, 0x000, 0x000,
|
||||
0x000, 0x000, 0x000, 0x000, 0x000, 0x000, 0x000, 0x000,
|
||||
0x000, 0x000, 0x000, 0x000, 0x000, 0x000, 0x000, 0x000,
|
||||
0x000, 0x000, 0x000, 0x000, 0x000, 0x000, 0x000, 0x000,
|
||||
0x040, 0x040, 0x040, 0x040, 0x040, 0x040, 0x040, 0x040,
|
||||
0x040, 0x040, 0x040, 0x040, 0x040, 0x040, 0x040, 0x040,
|
||||
0x080, 0x080, 0x080, 0x080, 0x080, 0x080, 0x080, 0x080,
|
||||
0x080, 0x080, 0x080, 0x080, 0x080, 0x080, 0x080, 0x080,
|
||||
0x0c0, 0x0c0, 0x0c0, 0x0c0, 0x0c0, 0x0c0, 0x0c0, 0x0c0,
|
||||
0x0c0, 0x0c0, 0x0c0, 0x0c0, 0x0c0, 0x0c0, 0x0c0, 0x0c0,
|
||||
0x100, 0x100, 0x100, 0x100, 0x100, 0x100, 0x100, 0x100,
|
||||
0x140, 0x140, 0x140, 0x140, 0x140, 0x140, 0x140, 0x140,
|
||||
0x180, 0x180, 0x180, 0x180, 0x180, 0x180, 0x180, 0x180,
|
||||
0x1c0, 0x1c0, 0x1c0, 0x1c0, 0x1c0, 0x1c0, 0x1c0, 0x1c0,
|
||||
0x200, 0x200, 0x200, 0x200, 0x200, 0x200, 0x200, 0x200,
|
||||
0x240, 0x240, 0x240, 0x240, 0x240, 0x240, 0x240, 0x240,
|
||||
0x280, 0x280, 0x280, 0x280, 0x280, 0x280, 0x280, 0x280,
|
||||
0x2c0, 0x2c0, 0x2c0, 0x2c0, 0x2c0, 0x2c0, 0x2c0, 0x2c0,
|
||||
0x300, 0x300, 0x300, 0x300, 0x340, 0x340, 0x340, 0x340,
|
||||
0x380, 0x380, 0x380, 0x380, 0x3c0, 0x3c0, 0x3c0, 0x3c0,
|
||||
0x400, 0x400, 0x400, 0x400, 0x440, 0x440, 0x440, 0x440,
|
||||
0x480, 0x480, 0x480, 0x480, 0x4c0, 0x4c0, 0x4c0, 0x4c0,
|
||||
0x500, 0x500, 0x500, 0x500, 0x540, 0x540, 0x540, 0x540,
|
||||
0x580, 0x580, 0x580, 0x580, 0x5c0, 0x5c0, 0x5c0, 0x5c0,
|
||||
0x600, 0x600, 0x640, 0x640, 0x680, 0x680, 0x6c0, 0x6c0,
|
||||
0x700, 0x700, 0x740, 0x740, 0x780, 0x780, 0x7c0, 0x7c0,
|
||||
0x800, 0x800, 0x840, 0x840, 0x880, 0x880, 0x8c0, 0x8c0,
|
||||
0x900, 0x900, 0x940, 0x940, 0x980, 0x980, 0x9c0, 0x9c0,
|
||||
0xa00, 0xa00, 0xa40, 0xa40, 0xa80, 0xa80, 0xac0, 0xac0,
|
||||
0xb00, 0xb00, 0xb40, 0xb40, 0xb80, 0xb80, 0xbc0, 0xbc0,
|
||||
0xc00, 0xc40, 0xc80, 0xcc0, 0xd00, 0xd40, 0xd80, 0xdc0,
|
||||
0xe00, 0xe40, 0xe80, 0xec0, 0xf00, 0xf40, 0xf80, 0xfc0};
|
||||
|
||||
static short HuffLength[] = {
|
||||
3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3,
|
||||
3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3,
|
||||
4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
|
||||
4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
|
||||
4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
|
||||
5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5,
|
||||
5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5,
|
||||
5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5,
|
||||
5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5,
|
||||
6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6,
|
||||
6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6,
|
||||
6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6,
|
||||
7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
|
||||
7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
|
||||
7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
|
||||
8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8};
|
||||
|
||||
unsigned char (*lzah_getbyte)();
|
||||
|
||||
static void lzah_inithuf();
|
||||
static void lzah_reorder();
|
||||
static void lzah_move();
|
||||
static void lzah_getbit();
|
||||
static void lzah_outchar();
|
||||
|
||||
static char lzah_buf[4096];
|
||||
static int lzah_bufptr;
|
||||
static int lzah_bitsavail;
|
||||
static int lzah_bits;
|
||||
static int Frequ[1000];
|
||||
static int ForwTree[1000];
|
||||
static int BackTree[1000];
|
||||
|
||||
void de_lzah(obytes)
|
||||
unsigned long obytes;
|
||||
{
|
||||
int i, i1, j, ch, byte, offs, skip;
|
||||
|
||||
lzah_inithuf();
|
||||
lzah_bitsavail = 0;
|
||||
for(i = 0; i < 4036; i++) {
|
||||
lzah_buf[i] = ' ';
|
||||
}
|
||||
lzah_bufptr = 4036;
|
||||
while(obytes != 0) {
|
||||
ch = ForwTree[T - 1];
|
||||
while(ch < T) {
|
||||
lzah_getbit();
|
||||
if(lzah_bits & 0x80) {
|
||||
ch = ch + 1;
|
||||
}
|
||||
ch = ForwTree[ch];
|
||||
}
|
||||
ch -= T;
|
||||
if(Frequ[T - 1] >= 0x8000) {
|
||||
lzah_reorder();
|
||||
}
|
||||
|
||||
i = BackTree[ch + T];
|
||||
do {
|
||||
j = ++Frequ[i];
|
||||
i1 = i + 1;
|
||||
if(Frequ[i1] < j) {
|
||||
while(Frequ[++i1] < j) ;
|
||||
i1--;
|
||||
Frequ[i] = Frequ[i1];
|
||||
Frequ[i1] = j;
|
||||
|
||||
j = ForwTree[i];
|
||||
BackTree[j] = i1;
|
||||
if(j < T) {
|
||||
BackTree[j + 1] = i1;
|
||||
}
|
||||
ForwTree[i] = ForwTree[i1];
|
||||
ForwTree[i1] = j;
|
||||
j = ForwTree[i];
|
||||
BackTree[j] = i;
|
||||
if(j < T) {
|
||||
BackTree[j + 1] = i;
|
||||
}
|
||||
i = i1;
|
||||
}
|
||||
i = BackTree[i];
|
||||
} while(i != 0);
|
||||
|
||||
if(ch < 256) {
|
||||
lzah_outchar((char)ch);
|
||||
obytes--;
|
||||
} else {
|
||||
if(lzah_bitsavail != 0) {
|
||||
byte = (lzah_bits << 1) & BYTEMASK;
|
||||
lzah_bits = (*lzah_getbyte)() & BYTEMASK;
|
||||
byte |= (lzah_bits >> lzah_bitsavail);
|
||||
lzah_bits = lzah_bits << (7 - lzah_bitsavail);
|
||||
} else {
|
||||
byte = (*lzah_getbyte)() & BYTEMASK;
|
||||
}
|
||||
offs = HuffCode[byte];
|
||||
skip = HuffLength[byte] - 2;
|
||||
while(skip-- != 0) {
|
||||
byte = byte + byte;
|
||||
lzah_getbit();
|
||||
if(lzah_bits & 0x80) {
|
||||
byte++;
|
||||
}
|
||||
}
|
||||
offs |= (byte & 0x3f);
|
||||
offs = ((lzah_bufptr - offs - 1) & 0xfff);
|
||||
ch = ch - 253;
|
||||
while(ch-- > 0) {
|
||||
lzah_outchar(lzah_buf[offs++ & 0xfff]);
|
||||
obytes--;
|
||||
if(obytes == 0) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void lzah_inithuf()
|
||||
{
|
||||
int i, j;
|
||||
|
||||
for(i = 0; i < N; i++) {
|
||||
Frequ[i] = 1;
|
||||
ForwTree[i] = i + T;
|
||||
BackTree[i + T] = i;
|
||||
}
|
||||
for(i = 0, j = N; j < T; i += 2, j++) {
|
||||
Frequ[j] = Frequ[i] + Frequ[i + 1];
|
||||
ForwTree[j] = i;
|
||||
BackTree[i] = j;
|
||||
BackTree[i + 1] = j;
|
||||
}
|
||||
Frequ[T] = 0xffff;
|
||||
BackTree[T - 1] = 0;
|
||||
}
|
||||
|
||||
static void lzah_reorder()
|
||||
{
|
||||
int i, j, k, l;
|
||||
|
||||
j = 0;
|
||||
for(i = 0; i < T; i++) {
|
||||
if(ForwTree[i] >= T) {
|
||||
Frequ[j] = ((Frequ[i] + 1) >> 1);
|
||||
ForwTree[j] = ForwTree[i];
|
||||
j++;
|
||||
}
|
||||
}
|
||||
for(i = 0, j = N; i < T; i += 2, j++) {
|
||||
k = i + 1;
|
||||
l = Frequ[i] + Frequ[k];
|
||||
Frequ[j] = l;
|
||||
k = j - 1;
|
||||
while(l < Frequ[k]) {
|
||||
k--;
|
||||
}
|
||||
k = k + 1;
|
||||
lzah_move(Frequ + k, Frequ + k + 1, j - k);
|
||||
Frequ[k] = l;
|
||||
lzah_move(ForwTree + k, ForwTree + k + 1, j - k);
|
||||
ForwTree[k] = i;
|
||||
}
|
||||
for(i = 0; i < T; i++) {
|
||||
k = ForwTree[i];
|
||||
if(k >= T) {
|
||||
BackTree[k] = i;
|
||||
} else {
|
||||
BackTree[k] = i;
|
||||
BackTree[k + 1] = i;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void lzah_move(p, q, n)
|
||||
int *p, *q, n;
|
||||
{
|
||||
if(p > q) {
|
||||
while(n-- > 0) {
|
||||
*q++ = *p++;
|
||||
}
|
||||
} else {
|
||||
p += n;
|
||||
q += n;
|
||||
while(n-- > 0) {
|
||||
*--q = *--p;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void lzah_getbit()
|
||||
{
|
||||
if(lzah_bitsavail != 0) {
|
||||
lzah_bits = lzah_bits + lzah_bits;
|
||||
lzah_bitsavail--;
|
||||
} else {
|
||||
lzah_bits = (*lzah_getbyte)() & BYTEMASK;
|
||||
lzah_bitsavail = 7;
|
||||
}
|
||||
}
|
||||
|
||||
static void lzah_outchar(ch)
|
||||
char ch;
|
||||
{
|
||||
*out_ptr++ = ch;
|
||||
lzah_buf[lzah_bufptr++] = ch;
|
||||
lzah_bufptr &= 0xfff;
|
||||
}
|
||||
#else /* DELZAH */
|
||||
int delzah; /* keep lint and some compilers happy */
|
||||
#endif /* DELZAH */
|
||||
|
314
macunpack/de_lzh.c
Executable file
314
macunpack/de_lzh.c
Executable file
@ -0,0 +1,314 @@
|
||||
#include "macunpack.h"
|
||||
#ifdef ZMA
|
||||
#define DELZH
|
||||
#endif /* ZMA */
|
||||
#ifdef LZH
|
||||
#define DELZH
|
||||
#endif /* LZH */
|
||||
#ifdef DELZH
|
||||
#include "globals.h"
|
||||
#include "../util/masks.h"
|
||||
#include "../fileio/wrfile.h"
|
||||
#include "bits_be.h"
|
||||
|
||||
/* This code is valid for bitsused upto 15. */
|
||||
#define DICBIT 13 /* 12(-lh4-) or 13(-lh5-) */
|
||||
#define UCHAR_MAX 255
|
||||
#define THRESHOLD 3
|
||||
|
||||
static int decoded;
|
||||
static int bitsused;
|
||||
static unsigned int blocksize;
|
||||
static unsigned int decode_c();
|
||||
static unsigned int decode_p();
|
||||
static void make_table();
|
||||
|
||||
/* lzh compression */
|
||||
void de_lzh(ibytes, obytes, data, bits)
|
||||
long ibytes;
|
||||
long obytes;
|
||||
char **data;
|
||||
int bits;
|
||||
{
|
||||
unsigned int i, r, c;
|
||||
int remains;
|
||||
|
||||
bit_be_inbytes = ibytes;
|
||||
bit_be_filestart = *data;
|
||||
bitsused = bits;
|
||||
bit_be_init_getbits();
|
||||
blocksize = 0;
|
||||
decoded = 0;
|
||||
r = 0;
|
||||
for(;;) {
|
||||
c = decode_c();
|
||||
if(decoded) {
|
||||
*data = bit_be_filestart;
|
||||
return;
|
||||
}
|
||||
if(c <= UCHAR_MAX) {
|
||||
out_ptr[r++] = c;
|
||||
obytes--;
|
||||
if(obytes == 0) {
|
||||
*data = bit_be_filestart;
|
||||
return;
|
||||
}
|
||||
} else {
|
||||
remains = c - (UCHAR_MAX + 1 - THRESHOLD);
|
||||
i = (r - decode_p() - 1);
|
||||
while(--remains >= 0) {
|
||||
out_ptr[r++] = out_ptr[i++];
|
||||
obytes--;
|
||||
if(obytes == 0) {
|
||||
*data = bit_be_filestart;
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#define MAXMATCH 256
|
||||
#define NC (UCHAR_MAX + MAXMATCH + 2 - THRESHOLD)
|
||||
#define CBIT 9
|
||||
#define CODE_BIT 16
|
||||
#define NP (DICBIT + 1)
|
||||
#define NT (CODE_BIT + 3)
|
||||
#define PBIT 4 /* smallest integer such that (1U << PBIT) > NP */
|
||||
#define TBIT 5 /* smallest integer such that (1U << TBIT) > NT */
|
||||
#if NT > NP
|
||||
# define NPT NT
|
||||
#else
|
||||
# define NPT NP
|
||||
#endif
|
||||
|
||||
static unsigned int left[2 * NC - 1], right[2 * NC - 1];
|
||||
static unsigned char c_len[NC], pt_len[NPT];
|
||||
static unsigned int c_table[4096], pt_table[256];
|
||||
|
||||
static void read_pt_len(nn, nbit, i_special)
|
||||
int nn;
|
||||
int nbit;
|
||||
int i_special;
|
||||
{
|
||||
int i, c, n;
|
||||
unsigned int mask;
|
||||
|
||||
n = bit_be_getbits(nbit);
|
||||
if (n == 0) {
|
||||
c = bit_be_getbits(nbit);
|
||||
for (i = 0; i < nn; i++) {
|
||||
pt_len[i] = 0;
|
||||
}
|
||||
for (i = 0; i < 256; i++) {
|
||||
pt_table[i] = c;
|
||||
}
|
||||
} else {
|
||||
i = 0;
|
||||
while (i < n) {
|
||||
c = bit_be_bitbuf >> (BITBUFSIZ - 3);
|
||||
if (c == 7) {
|
||||
mask = (unsigned) 1 << (BITBUFSIZ - 1 - 3);
|
||||
while (mask & bit_be_bitbuf) {
|
||||
mask >>= 1;
|
||||
c++;
|
||||
}
|
||||
}
|
||||
bit_be_fillbuf((c < 7) ? 3 : c - 3);
|
||||
pt_len[i++] = c;
|
||||
if (i == i_special) {
|
||||
c = bit_be_getbits(2);
|
||||
while (--c >= 0) {
|
||||
pt_len[i++] = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
while (i < nn) {
|
||||
pt_len[i++] = 0;
|
||||
}
|
||||
make_table(nn, pt_len, 8, pt_table);
|
||||
}
|
||||
}
|
||||
|
||||
static void read_c_len()
|
||||
{
|
||||
int i, c, n;
|
||||
unsigned int mask;
|
||||
|
||||
n = bit_be_getbits(CBIT);
|
||||
if (n == 0) {
|
||||
c = bit_be_getbits(CBIT);
|
||||
for (i = 0; i < NC; i++) {
|
||||
c_len[i] = 0;
|
||||
}
|
||||
for (i = 0; i < 4096; i++) {
|
||||
c_table[i] = c;
|
||||
}
|
||||
} else {
|
||||
i = 0;
|
||||
while (i < n) {
|
||||
c = pt_table[bit_be_bitbuf >> (BITBUFSIZ - 8)];
|
||||
if (c >= NT) {
|
||||
mask = (unsigned) 1 << (BITBUFSIZ - 1 - 8);
|
||||
do {
|
||||
if (bit_be_bitbuf & mask) {
|
||||
c = right[c];
|
||||
} else {
|
||||
c = left [c];
|
||||
}
|
||||
mask >>= 1;
|
||||
} while (c >= NT);
|
||||
}
|
||||
bit_be_fillbuf((int)pt_len[c]);
|
||||
if (c <= 2) {
|
||||
if (c == 0) {
|
||||
c = 1;
|
||||
} else if (c == 1) {
|
||||
c = bit_be_getbits(4) + 3;
|
||||
} else {
|
||||
c = bit_be_getbits(CBIT) + 20;
|
||||
}
|
||||
while (--c >= 0) {
|
||||
c_len[i++] = 0;
|
||||
}
|
||||
} else {
|
||||
c_len[i++] = c - 2;
|
||||
}
|
||||
}
|
||||
while (i < NC) {
|
||||
c_len[i++] = 0;
|
||||
}
|
||||
make_table(NC, c_len, 12, c_table);
|
||||
}
|
||||
}
|
||||
|
||||
static unsigned int decode_c()
|
||||
{
|
||||
unsigned int j, mask;
|
||||
|
||||
if (blocksize == 0) {
|
||||
blocksize = bit_be_getbits(16);
|
||||
if (blocksize == 0) {
|
||||
decoded = 1;
|
||||
return 0;
|
||||
}
|
||||
read_pt_len(NT, TBIT, 3);
|
||||
read_c_len();
|
||||
read_pt_len(bitsused + 1, PBIT, -1);
|
||||
}
|
||||
blocksize--;
|
||||
j = c_table[bit_be_bitbuf >> (BITBUFSIZ - 12)];
|
||||
if (j >= NC) {
|
||||
mask = (unsigned) 1 << (BITBUFSIZ - 1 - 12);
|
||||
do {
|
||||
if (bit_be_bitbuf & mask) {
|
||||
j = right[j];
|
||||
} else {
|
||||
j = left [j];
|
||||
}
|
||||
mask >>= 1;
|
||||
} while (j >= NC);
|
||||
}
|
||||
bit_be_fillbuf((int)c_len[j]);
|
||||
return j;
|
||||
}
|
||||
|
||||
static unsigned int decode_p()
|
||||
{
|
||||
unsigned int j, mask;
|
||||
|
||||
j = pt_table[bit_be_bitbuf >> (BITBUFSIZ - 8)];
|
||||
if (j > bitsused) {
|
||||
mask = (unsigned) 1 << (BITBUFSIZ - 1 - 8);
|
||||
do {
|
||||
if (bit_be_bitbuf & mask) {
|
||||
j = right[j];
|
||||
} else {
|
||||
j = left [j];
|
||||
}
|
||||
mask >>= 1;
|
||||
} while (j > bitsused);
|
||||
}
|
||||
bit_be_fillbuf((int)pt_len[j]);
|
||||
if (j != 0) {
|
||||
j = ((unsigned) 1 << (j - 1)) + bit_be_getbits((int) (j - 1));
|
||||
}
|
||||
return j;
|
||||
}
|
||||
|
||||
static void make_table(nchar, bitlen, tablebits, table)
|
||||
int nchar;
|
||||
unsigned char bitlen[];
|
||||
int tablebits;
|
||||
unsigned int table[];
|
||||
{
|
||||
unsigned int count[17], weight[17], start[18], *p;
|
||||
unsigned int i, k, len, ch, jutbits, avail, nextcode, mask;
|
||||
|
||||
for (i = 1; i <= 16; i++) {
|
||||
count[i] = 0;
|
||||
}
|
||||
for (i = 0; i < nchar; i++) {
|
||||
count[bitlen[i]]++;
|
||||
}
|
||||
|
||||
start[1] = 0;
|
||||
for (i = 1; i <= 16; i++) {
|
||||
start[i + 1] = start[i] + (count[i] << (16 - i));
|
||||
}
|
||||
|
||||
jutbits = 16 - tablebits;
|
||||
for (i = 1; i <= tablebits; i++) {
|
||||
start[i] >>= jutbits;
|
||||
weight[i] = (unsigned) 1 << (tablebits - i);
|
||||
}
|
||||
while (i <= 16) {
|
||||
weight[i] = (unsigned) 1 << (16 - i);
|
||||
i++;
|
||||
}
|
||||
|
||||
i = start[tablebits + 1] >> jutbits;
|
||||
if (i != (unsigned int)((unsigned) 1 << 16)) {
|
||||
k = 1 << tablebits;
|
||||
while (i != k) {
|
||||
table[i++] = 0;
|
||||
}
|
||||
}
|
||||
|
||||
avail = nchar;
|
||||
mask = (unsigned) 1 << (15 - tablebits);
|
||||
for (ch = 0; ch < nchar; ch++) {
|
||||
if ((len = bitlen[ch]) == 0) {
|
||||
continue;
|
||||
}
|
||||
nextcode = start[len] + weight[len];
|
||||
if (len <= tablebits) {
|
||||
for (i = start[len]; i < nextcode; i++) {
|
||||
table[i] = ch;
|
||||
}
|
||||
} else {
|
||||
k = start[len];
|
||||
p = &table[k >> jutbits];
|
||||
i = len - tablebits;
|
||||
while (i != 0) {
|
||||
if (*p == 0) {
|
||||
right[avail] = left[avail] = 0;
|
||||
*p = avail++;
|
||||
}
|
||||
if (k & mask) {
|
||||
p = &right[*p];
|
||||
} else {
|
||||
p = &left[*p];
|
||||
}
|
||||
k <<= 1;
|
||||
i--;
|
||||
}
|
||||
*p = ch;
|
||||
}
|
||||
start[len] = nextcode;
|
||||
}
|
||||
}
|
||||
#else /* DELZH */
|
||||
int delzh; /* keep lint and some compilers happy */
|
||||
#endif /* DELZH */
|
||||
|
558
macunpack/dia.c
Executable file
558
macunpack/dia.c
Executable file
@ -0,0 +1,558 @@
|
||||
#include "macunpack.h"
|
||||
#ifdef DIA
|
||||
#include "globals.h"
|
||||
#include "dia.h"
|
||||
#include "../util/curtime.h"
|
||||
#include "../util/masks.h"
|
||||
#include "../fileio/machdr.h"
|
||||
#include "../fileio/wrfile.h"
|
||||
#include "../fileio/kind.h"
|
||||
#include "../util/util.h"
|
||||
|
||||
extern char *malloc();
|
||||
extern char *realloc();
|
||||
|
||||
static unsigned char *dia_archive;
|
||||
static int dia_archive_size;
|
||||
static int dia_max_archive_size;
|
||||
static int dia_finfo;
|
||||
static int dia_method;
|
||||
static unsigned char *dia_archive_ptr;
|
||||
static unsigned char *dia_header_ptr;
|
||||
static unsigned char *dia_header_last;
|
||||
static int dia_forklength;
|
||||
static int dia_cforklength;
|
||||
static unsigned char dia_bitbuf[BCHUNKSIZE];
|
||||
static int dia_LZtab[BCHUNKSIZE];
|
||||
static unsigned char *dia_bit_base;
|
||||
static int dia_imask;
|
||||
|
||||
static void dia_folder();
|
||||
static void dia_file();
|
||||
static void dia_getlength();
|
||||
static void dia_skipfork();
|
||||
static void dia_getfork();
|
||||
static void dia_getblock();
|
||||
static int dia_decode();
|
||||
static int dia_prevbit();
|
||||
|
||||
void dia(bin_hdr)
|
||||
unsigned char *bin_hdr;
|
||||
{
|
||||
int i, folder, nlength;
|
||||
unsigned char hdr;
|
||||
unsigned char *header;
|
||||
|
||||
dir_skip = 0;
|
||||
for(i = 0; i < INFOBYTES; i++) {
|
||||
info[i] = 0;
|
||||
}
|
||||
if(in_data_size > dia_max_archive_size) {
|
||||
if(dia_archive == NULL) {
|
||||
dia_archive = (unsigned char *)malloc((unsigned)in_data_size);
|
||||
} else {
|
||||
dia_archive = (unsigned char *)realloc((char *)dia_archive,
|
||||
(unsigned)in_data_size);
|
||||
}
|
||||
if(dia_archive == 0) {
|
||||
(void)fprintf(stderr, "Insufficient memory.\n");
|
||||
exit(1);
|
||||
}
|
||||
dia_max_archive_size = in_data_size;
|
||||
}
|
||||
dia_archive_size = in_data_size;
|
||||
if(fread((char *)dia_archive, 1, in_data_size, infp) != in_data_size) {
|
||||
(void)fprintf(stderr, "Can't read archive.\n");
|
||||
#ifdef SCAN
|
||||
do_error("macunpack: Can't read archive");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
nlength = bin_hdr[I_NAMEOFF] & BYTEMASK;
|
||||
if(!strncmp((char *)bin_hdr + I_NAMEOFF + nlength - 1, " \272", 2)) {
|
||||
nlength -= 2;
|
||||
}
|
||||
info[I_NAMEOFF] = nlength;
|
||||
for(i = 1; i <= nlength; i++) {
|
||||
info[I_NAMEOFF + i] = bin_hdr[I_NAMEOFF + i];
|
||||
}
|
||||
hdr = *dia_archive;
|
||||
folder = hdr & IS_FOLDER;
|
||||
dia_finfo = hdr & F_INFO;
|
||||
if(hdr & VOLUME) {
|
||||
(void)fprintf(stderr, "Multi-segment archives not implemented.\n");
|
||||
#ifdef SCAN
|
||||
do_error("macunpack: Multi-segment archive");
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
if(hdr & CRYPTED) {
|
||||
(void)fprintf(stderr, "Encrypted archives not implemented.\n");
|
||||
#ifdef SCAN
|
||||
do_idf("", PROTECTED);
|
||||
#endif /* SCAN */
|
||||
exit(1);
|
||||
}
|
||||
i = (hdr & N_BLOCKS) + 1;
|
||||
header = (unsigned char *)malloc((unsigned)(i * CHUNKSIZE));
|
||||
dia_archive_ptr = dia_archive + 1;
|
||||
dia_header_last = header;
|
||||
dia_method = 0;
|
||||
while(i-- > 0) {
|
||||
dia_getblock(&dia_archive_ptr, &dia_header_last);
|
||||
}
|
||||
dia_header_ptr = header;
|
||||
if(folder) {
|
||||
dia_folder((unsigned char *)NULL);
|
||||
} else {
|
||||
dia_file(*dia_header_ptr++, (unsigned char *)NULL);
|
||||
}
|
||||
free((char *)header);
|
||||
}
|
||||
|
||||
static void dia_folder(name)
|
||||
unsigned char *name;
|
||||
{
|
||||
unsigned char lname[32];
|
||||
int i, length, doit;
|
||||
unsigned char indicator, *old_ptr;
|
||||
|
||||
if(name != NULL) {
|
||||
for(i = 0; i < INFOBYTES; i++) {
|
||||
info[i] = 0;
|
||||
}
|
||||
length = *name++ & REMAINS;
|
||||
info[I_NAMEOFF] = length;
|
||||
for(i = 1; i <= length; i++) {
|
||||
info[I_NAMEOFF + i] = *name++;
|
||||
}
|
||||
} else {
|
||||
length = info[I_NAMEOFF];
|
||||
}
|
||||
if(dia_finfo) {
|
||||
dia_header_ptr += 20;
|
||||
}
|
||||
if(!dir_skip) {
|
||||
doit = 1;
|
||||
if(list) {
|
||||
transname(info + I_NAMEOFF + 1, (char *)lname, length);
|
||||
do_indent(indent);
|
||||
(void)fprintf(stderr, "folder=\"%s\"", lname);
|
||||
if(query) {
|
||||
doit = do_query();
|
||||
} else {
|
||||
(void)fputc('\n', stderr);
|
||||
}
|
||||
if(doit) {
|
||||
indent++;
|
||||
} else {
|
||||
dir_skip = 1;
|
||||
}
|
||||
}
|
||||
if(doit && !info_only) {
|
||||
do_mkdir((char *)lname, info);
|
||||
}
|
||||
} else {
|
||||
dir_skip++;
|
||||
}
|
||||
while(dia_header_ptr < dia_header_last) {
|
||||
indicator = *dia_header_ptr;
|
||||
if(indicator & LEAVE_FOLDER) {
|
||||
*dia_header_ptr = indicator & ~LEAVE_FOLDER;
|
||||
break;
|
||||
} else if(indicator & ONLY_FOLDER) {
|
||||
if(indicator == ONLY_FOLDER) {
|
||||
dia_header_ptr++;
|
||||
} else {
|
||||
*dia_header_ptr -= 1;
|
||||
}
|
||||
break;
|
||||
} else if(indicator & FOLDER) {
|
||||
old_ptr = dia_header_ptr;
|
||||
dia_header_ptr += (indicator & REMAINS) + 1;
|
||||
dia_folder(old_ptr);
|
||||
} else {
|
||||
dia_header_ptr++;
|
||||
old_ptr = dia_header_ptr;
|
||||
dia_header_ptr += (*old_ptr & REMAINS) + 1;
|
||||
dia_file(indicator, old_ptr);
|
||||
}
|
||||
}
|
||||
if(!dir_skip) {
|
||||
if(doit) {
|
||||
indent--;
|
||||
if(!info_only) {
|
||||
enddir();
|
||||
}
|
||||
do_indent(indent);
|
||||
(void)fprintf(stderr, "leaving folder \"%s\"\n", lname);
|
||||
}
|
||||
} else {
|
||||
dir_skip--;
|
||||
}
|
||||
}
|
||||
|
||||
static void dia_file(indicator, name)
|
||||
unsigned char indicator, *name;
|
||||
{
|
||||
unsigned char lname[32];
|
||||
int i, length, doit;
|
||||
int n_data, n_rsrc;
|
||||
unsigned char *old_archive_ptr;
|
||||
char ftype[5], fauth[5];
|
||||
int dataLength, rsrcLength;
|
||||
int cdataLength, crsrcLength;
|
||||
int dataMethod, rsrcMethod;
|
||||
unsigned long curtime;
|
||||
|
||||
if(name != NULL) {
|
||||
for(i = 0; i < INFOBYTES; i++) {
|
||||
info[i] = 0;
|
||||
}
|
||||
length = *name++ & REMAINS;
|
||||
info[I_NAMEOFF] = length;
|
||||
for(i = 1; i <= length; i++) {
|
||||
info[I_NAMEOFF + i] = *name++;
|
||||
}
|
||||
} else {
|
||||
length = info[I_NAMEOFF];
|
||||
}
|
||||
for(i = 0; i < 4; i++) {
|
||||
info[I_TYPEOFF + i] = *dia_header_ptr++;
|
||||
}
|
||||
for(i = 0; i < 4; i++) {
|
||||
info[I_AUTHOFF + i] = *dia_header_ptr++;
|
||||
}
|
||||
if(indicator & DATE_PRESENT) {
|
||||
for(i = 0; i < 4; i++) {
|
||||
info[I_CTIMOFF + i] = *dia_header_ptr++;
|
||||
}
|
||||
for(i = 0; i < 4; i++) {
|
||||
info[I_MTIMOFF + i] = *dia_header_ptr++;
|
||||
}
|
||||
} else {
|
||||
curtime = (unsigned long)time((time_t *)0) + TIMEDIFF;
|
||||
put4(info + I_CTIMOFF, curtime);
|
||||
put4(info + I_MTIMOFF, curtime);
|
||||
}
|
||||
if(dia_finfo) {
|
||||
for(i = 0; i < 6; i++) {
|
||||
info[I_FLAGOFF + i] = *dia_header_ptr++;
|
||||
}
|
||||
}
|
||||
n_data = 0;
|
||||
if(indicator & HAS_DATA) {
|
||||
if(indicator & SHORT_DATA) {
|
||||
n_data = 1;
|
||||
} else {
|
||||
n_data = *dia_header_ptr++ + 1;
|
||||
}
|
||||
}
|
||||
n_rsrc = 0;
|
||||
if(indicator & HAS_RSRC) {
|
||||
if(indicator & SHORT_RSRC) {
|
||||
n_rsrc = 1;
|
||||
} else {
|
||||
n_rsrc = *dia_header_ptr++ + 1;
|
||||
}
|
||||
}
|
||||
if(!dir_skip) {
|
||||
old_archive_ptr = dia_archive_ptr;
|
||||
dia_getlength(n_data);
|
||||
dataLength = dia_forklength;
|
||||
cdataLength = dia_cforklength;
|
||||
dataMethod = dia_method;
|
||||
dia_getlength(n_rsrc);
|
||||
rsrcLength = dia_forklength;
|
||||
crsrcLength = dia_cforklength;
|
||||
rsrcMethod = dia_method;
|
||||
dia_archive_ptr = old_archive_ptr;
|
||||
put4(info + I_DLENOFF, (unsigned long)dataLength);
|
||||
put4(info + I_RLENOFF, (unsigned long)rsrcLength);
|
||||
if(list) {
|
||||
transname(info + I_NAMEOFF + 1, (char *)lname, length);
|
||||
do_indent(indent);
|
||||
transname(info + I_TYPEOFF, ftype, 4);
|
||||
transname(info + I_AUTHOFF, fauth, 4);
|
||||
(void)fprintf(stderr,
|
||||
"name=\"%s\", type=%4.4s, author=%4.4s, data=%ld, rsrc=%ld",
|
||||
lname, ftype, fauth, (long)dataLength, (long)rsrcLength);
|
||||
if(info_only) {
|
||||
doit = 0;
|
||||
} else {
|
||||
doit = 1;
|
||||
}
|
||||
if(query) {
|
||||
doit = do_query();
|
||||
} else {
|
||||
(void)fputc('\n', stderr);
|
||||
}
|
||||
} else {
|
||||
doit = 1;
|
||||
}
|
||||
} else {
|
||||
dia_skipfork(n_data);
|
||||
dia_skipfork(n_rsrc);
|
||||
return;
|
||||
}
|
||||
if(doit) {
|
||||
define_name((char *)lname);
|
||||
start_info(info, (unsigned long)rsrcLength, (unsigned long)dataLength);
|
||||
}
|
||||
if(verbose) {
|
||||
(void)fprintf(stderr, "\tData: ");
|
||||
if(dataLength == 0) {
|
||||
(void)fprintf(stderr, "empty");
|
||||
} else if(dataMethod == NOCOMP) {
|
||||
(void)fprintf(stderr, "No compression");
|
||||
} else {
|
||||
if(dataMethod != COMP) {
|
||||
(void)fprintf(stderr, "Partial ");
|
||||
}
|
||||
(void)fprintf(stderr, "LZFK compressed (%4.1f%%)",
|
||||
100.0 * cdataLength / dataLength);
|
||||
}
|
||||
}
|
||||
if(doit) {
|
||||
start_data();
|
||||
dia_getfork(n_data);
|
||||
} else {
|
||||
dia_skipfork(n_data);
|
||||
}
|
||||
if(verbose) {
|
||||
(void)fprintf(stderr, ", Rsrc: ");
|
||||
if(rsrcLength == 0) {
|
||||
(void)fprintf(stderr, "empty");
|
||||
} else if(rsrcMethod == NOCOMP) {
|
||||
(void)fprintf(stderr, "No compression");
|
||||
} else {
|
||||
if(rsrcMethod != COMP) {
|
||||
(void)fprintf(stderr, "Partial ");
|
||||
}
|
||||
(void)fprintf(stderr, "LZFK compressed (%4.1f%%)",
|
||||
100.0 * crsrcLength / rsrcLength);
|
||||
}
|
||||
}
|
||||
if(doit) {
|
||||
start_rsrc();
|
||||
dia_getfork(n_rsrc);
|
||||
} else {
|
||||
dia_skipfork(n_rsrc);
|
||||
}
|
||||
if(verbose) {
|
||||
(void)fprintf(stderr, ".\n");
|
||||
}
|
||||
if(doit) {
|
||||
end_file();
|
||||
}
|
||||
}
|
||||
|
||||
static void dia_getlength(nblocks)
|
||||
int nblocks;
|
||||
{
|
||||
int length;
|
||||
unsigned char *arch_ptr, *block_ptr;
|
||||
unsigned char block[CHUNKSIZE];
|
||||
|
||||
dia_method = 0;
|
||||
dia_forklength = 0;
|
||||
dia_cforklength = 0;
|
||||
while(nblocks > 1) {
|
||||
nblocks--;
|
||||
length = get2((char *)dia_archive_ptr);
|
||||
if(length >= 0x8000) {
|
||||
length = 0x10000 - length;
|
||||
dia_method |= NOCOMP;
|
||||
} else {
|
||||
dia_method |= COMP;
|
||||
}
|
||||
dia_forklength += CHUNKSIZE;
|
||||
dia_cforklength += length + 2;
|
||||
dia_archive_ptr += length + 2;
|
||||
}
|
||||
if(nblocks == 1) {
|
||||
arch_ptr = dia_archive_ptr;
|
||||
block_ptr = block;
|
||||
dia_getblock(&arch_ptr, &block_ptr);
|
||||
dia_forklength += block_ptr - block;
|
||||
dia_cforklength += arch_ptr - dia_archive_ptr;
|
||||
dia_archive_ptr = arch_ptr;
|
||||
}
|
||||
}
|
||||
|
||||
static void dia_skipfork(nblocks)
|
||||
int nblocks;
|
||||
{
|
||||
int length;
|
||||
|
||||
while(nblocks-- > 0) {
|
||||
length = get2((char *)dia_archive_ptr);
|
||||
if(length >= 0x8000) {
|
||||
length = 0x10000 - length;
|
||||
}
|
||||
dia_archive_ptr += length + 2;
|
||||
}
|
||||
}
|
||||
|
||||
static void dia_getfork(nblocks)
|
||||
int nblocks;
|
||||
{
|
||||
while(nblocks-- > 0) {
|
||||
dia_getblock(&dia_archive_ptr, (unsigned char **)&out_ptr);
|
||||
}
|
||||
}
|
||||
|
||||
static void dia_getblock(archive_ptr, block_ptr)
|
||||
unsigned char **archive_ptr, **block_ptr;
|
||||
{
|
||||
int length, i;
|
||||
unsigned char *arch_ptr, *bl_ptr;
|
||||
|
||||
arch_ptr = *archive_ptr;
|
||||
bl_ptr = *block_ptr;
|
||||
length = get2((char *)arch_ptr);
|
||||
arch_ptr += 2;
|
||||
if(length >= 0x8000) {
|
||||
length = 0x10000 - length;
|
||||
for(i = 0; i < length; i++) {
|
||||
*bl_ptr++ = *arch_ptr++;
|
||||
}
|
||||
*block_ptr += length;
|
||||
dia_method |= NOCOMP;
|
||||
} else {
|
||||
*block_ptr += dia_decode(arch_ptr, bl_ptr, length);
|
||||
dia_method |= COMP;
|
||||
}
|
||||
*archive_ptr += length + 2;
|
||||
}
|
||||
|
||||
static int dia_decode(ibuff, obuff, in_length)
|
||||
unsigned char *ibuff, *obuff; int in_length;
|
||||
{
|
||||
int nbits, set_zero, i, j;
|
||||
unsigned char *bitbuf_ptr;
|
||||
int count[4];
|
||||
int *LZtab_ptr;
|
||||
unsigned char *out_ptr, *buf_ptr, *in_ptr;
|
||||
int omask;
|
||||
int LZcount;
|
||||
int *length_ptr, *nchars_ptr;
|
||||
int *offsn_ptr, length, nchars, offset;
|
||||
int *offs_ptr[4];
|
||||
int nwords;
|
||||
|
||||
in_ptr = ibuff + in_length;
|
||||
nbits = *--in_ptr;
|
||||
nbits |= (*--in_ptr << 8);
|
||||
if(nbits == WORDMASK) {
|
||||
nbits = *--in_ptr;
|
||||
nbits |= (*--in_ptr << 8);
|
||||
nbits = nbits + WORDMASK;
|
||||
}
|
||||
bitbuf_ptr = dia_bitbuf + BCHUNKSIZE;
|
||||
*--bitbuf_ptr = *--in_ptr;
|
||||
set_zero = 0;
|
||||
dia_bit_base = bitbuf_ptr;
|
||||
dia_imask = 1 << (7 - (nbits & 7));
|
||||
if(dia_prevbit()) {
|
||||
set_zero = 1;
|
||||
}
|
||||
for(i = 0; i < nbits; i++) {
|
||||
if(set_zero) {
|
||||
*--bitbuf_ptr = 0;
|
||||
} else {
|
||||
*--bitbuf_ptr = *--in_ptr;
|
||||
}
|
||||
if(dia_prevbit()) {
|
||||
set_zero = !set_zero;
|
||||
}
|
||||
}
|
||||
/* Now we have the bits in longitudal order; reorder them */
|
||||
nwords = ((dia_bit_base - bitbuf_ptr) >> 1);
|
||||
for(i = 0; i < nwords; i++) {
|
||||
dia_LZtab[i] = 0;
|
||||
}
|
||||
omask = 1;
|
||||
for(i = 0; i < 16; i++) {
|
||||
j = nwords;
|
||||
LZtab_ptr = dia_LZtab + nwords;
|
||||
while(j-- > 0) {
|
||||
LZtab_ptr--;
|
||||
if(dia_prevbit()) {
|
||||
*LZtab_ptr |= omask;
|
||||
}
|
||||
}
|
||||
omask <<= 1;
|
||||
}
|
||||
LZcount = nwords / 3;
|
||||
/* At this point we have in LZtab LZcount triples. Each triple consists
|
||||
of the following parts:
|
||||
nchars: the number of characters to take from input
|
||||
length: the number of characters - 1 to copy from output
|
||||
offset: the offset in the output buffer
|
||||
The ordering is as follows:
|
||||
1. lengths
|
||||
2. nchars
|
||||
3. offsets for length 0
|
||||
4. offsets for length 1
|
||||
5. offsets for length 2
|
||||
6. offsets for length 3
|
||||
7. offsets for other lengths
|
||||
*/
|
||||
/* Now first count the occurences of lengths 0 to 3 */
|
||||
count[0] = 0;
|
||||
count[1] = 0;
|
||||
count[2] = 0;
|
||||
count[3] = 0;
|
||||
for(i = 0; i < LZcount; i++) {
|
||||
if((j = dia_LZtab[i]) < 4) {
|
||||
count[j]++;
|
||||
}
|
||||
}
|
||||
length_ptr = dia_LZtab;
|
||||
nchars_ptr = dia_LZtab + LZcount;
|
||||
offs_ptr[0] = nchars_ptr + LZcount;
|
||||
offs_ptr[1] = offs_ptr[0] + count[0];
|
||||
offs_ptr[2] = offs_ptr[1] + count[1];
|
||||
offs_ptr[3] = offs_ptr[2] + count[2];
|
||||
offsn_ptr = offs_ptr[3] + count[3];
|
||||
out_ptr = obuff;
|
||||
for(i = 0; i < LZcount; i++) {
|
||||
length = *length_ptr++;
|
||||
nchars = *nchars_ptr++;
|
||||
if(length < 4) {
|
||||
offset = *offs_ptr[length]++;
|
||||
} else {
|
||||
offset = *offsn_ptr++;
|
||||
}
|
||||
while(nchars-- > 0) {
|
||||
*out_ptr++ = *ibuff++;
|
||||
}
|
||||
buf_ptr = out_ptr - length - offset - 1;
|
||||
while(length-- >= 0) {
|
||||
*out_ptr++ = *buf_ptr++;
|
||||
}
|
||||
}
|
||||
i = in_ptr - ibuff;
|
||||
while(i-- > 0) {
|
||||
*out_ptr++ = *ibuff++;
|
||||
}
|
||||
return out_ptr - obuff;
|
||||
}
|
||||
|
||||
static int dia_prevbit()
|
||||
{
|
||||
int c;
|
||||
|
||||
if(dia_imask == 0x100) {
|
||||
dia_bit_base--;
|
||||
dia_imask = 1;
|
||||
}
|
||||
c = *dia_bit_base & dia_imask;
|
||||
dia_imask <<= 1;
|
||||
return c;
|
||||
}
|
||||
#else /* DIA */
|
||||
int dia; /* keep lint and some compilers happy */
|
||||
#endif /* DIA */
|
||||
|
22
macunpack/dia.h
Executable file
22
macunpack/dia.h
Executable file
@ -0,0 +1,22 @@
|
||||
#define IS_FOLDER 0x80
|
||||
#define F_INFO 0x40
|
||||
#define VOLUME 0x30
|
||||
#define CRYPTED 0x08
|
||||
#define N_BLOCKS 0x07
|
||||
|
||||
#define LEAVE_FOLDER 0x80
|
||||
#define ONLY_FOLDER 0x40
|
||||
#define FOLDER 0x20
|
||||
#define DATE_PRESENT 0x10
|
||||
#define HAS_DATA 0x08
|
||||
#define HAS_RSRC 0x04
|
||||
#define SHORT_DATA 0x02
|
||||
#define SHORT_RSRC 0x01
|
||||
#define REMAINS 0x1f
|
||||
|
||||
#define CHUNKSIZE 32767
|
||||
#define BCHUNKSIZE (CHUNKSIZE * 16 / 7)
|
||||
|
||||
#define NOCOMP 1
|
||||
#define COMP 2
|
||||
|
BIN
macunpack/dia.o
Normal file
BIN
macunpack/dia.o
Normal file
Binary file not shown.
75
macunpack/dir.c
Executable file
75
macunpack/dir.c
Executable file
@ -0,0 +1,75 @@
|
||||
#include "globals.h"
|
||||
#include "../fileio/machdr.h"
|
||||
#include "../fileio/wrfile.h"
|
||||
#include "../util/util.h"
|
||||
#include "../util/masks.h"
|
||||
|
||||
extern char *malloc();
|
||||
extern char *realloc();
|
||||
|
||||
static char *dir_stack;
|
||||
static int dir_ptr = -64;
|
||||
static int dir_max;
|
||||
|
||||
void dir(hdr)
|
||||
char *hdr;
|
||||
{
|
||||
int doit;
|
||||
|
||||
if((hdr[I_NAMEOFF] & BYTEMASK) == 0x80) {
|
||||
if(dir_skip) {
|
||||
dir_skip--;
|
||||
return;
|
||||
}
|
||||
indent--;
|
||||
if(list) {
|
||||
do_indent(indent);
|
||||
(void)fprintf(stderr, "leaving folder \"%s\"\n",
|
||||
dir_stack + dir_ptr);
|
||||
}
|
||||
if(!info_only) {
|
||||
enddir();
|
||||
}
|
||||
dir_ptr -= 64;
|
||||
return;
|
||||
}
|
||||
if(dir_skip) {
|
||||
dir_skip++;
|
||||
return;
|
||||
}
|
||||
dir_ptr += 64;
|
||||
if(dir_ptr == dir_max) {
|
||||
if(dir_max == 0) {
|
||||
dir_stack = malloc(64);
|
||||
} else {
|
||||
dir_stack = realloc(dir_stack, (unsigned)dir_max + 64);
|
||||
}
|
||||
dir_max += 64;
|
||||
if(dir_stack == NULL) {
|
||||
(void)fprintf(stderr, "Insufficient memory\n");
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
transname(hdr + I_NAMEOFF + 1, dir_stack + dir_ptr,
|
||||
(int)(hdr[I_NAMEOFF] & 0x7f));
|
||||
doit = 1;
|
||||
if(list) {
|
||||
do_indent(indent);
|
||||
(void)fprintf(stderr, "folder=\"%s\"", dir_stack + dir_ptr);
|
||||
if(query) {
|
||||
doit = do_query();
|
||||
} else {
|
||||
(void)fputc('\n', stderr);
|
||||
}
|
||||
}
|
||||
if(!doit) {
|
||||
dir_ptr -= 64;
|
||||
dir_skip = 1;
|
||||
return;
|
||||
}
|
||||
if(!info_only) {
|
||||
do_mkdir(dir_stack + dir_ptr, hdr);
|
||||
}
|
||||
indent++;
|
||||
}
|
||||
|
BIN
macunpack/dir.o
Normal file
BIN
macunpack/dir.o
Normal file
Binary file not shown.
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user