sears@dungeon.enet.dec.com (Chris Sears) (11/15/90)
To whom it may concern: Included below is a decrypter for Adobe Type-1 encrypted fonts. It generates very simple PostScript. It does however have a bug with SEAC accented characters that I can't seem to figure out. So, as long as you don't do flying logos in Norwegian, its the cat's meow. In the near future I'll fix the SEAC bug and add character size definitions. If you or anyone you know happen to know anything about SEAC, I'd be mighty appreciative to hear from y'all. Chris Sears sears@dungeon.pa.dec.com #!/bin/sh # This is a shell archive (shar 3.24) # made 11/15/1990 02:06 UTC by ???@blofeld.pa.dec.com # Source directory /nfs/catacomb/cc1/sears/untype1 # # existing files WILL be overwritten # # This shar contains: # length mode name # ------ ---------- ------------------------------------------ # 364 -rw-rw-rw- Makefile # 3658 -rw-r--r-- README # 5322 -rw-r--r-- chars.c # 1829 -rw-rw-rw- eexec.c # 3369 -rw-r--r-- header.ps # 895 -rw-r--r-- trailer.ps # 535 -rwxr-xr-x untype1 # 9054 -rw-r--r-- un-adobe.hqx # 42 -rw-r--r-- view_pre.ps # 618 -rw-r--r-- view_post.ps # if touch 2>&1 | fgrep '[-amc]' > /dev/null then TOUCH=touch else TOUCH=true fi # ============= Makefile ============== echo "x - extracting Makefile (Text)" sed 's/^X//' << 'SHAR_EOF' > Makefile && XCFLAGS = -g X Xall: eexec chars X Xeexec: eexec.o X cc ${CFLAGS} -o eexec eexec.o X Xeexec.o: X cc ${CFLAGS} -c eexec.c X Xchars: chars.o X cc ${CFLAGS} -o chars chars.o X Xchars.o: X cc ${CFLAGS} -c chars.c X Xclean: X rm -f *.o eexec chars untype1.shar X Xshar: X shar Makefile README chars.c eexec.c header.ps trailer.ps untype1 un-adobe.hqx view_pre.ps view_post.ps >untype1.shar SHAR_EOF $TOUCH -am 1114140890 Makefile && chmod 0666 Makefile || echo "restore of Makefile failed" set `wc -c Makefile`;Wc_c=$1 if test "$Wc_c" != "364"; then echo original size 364, current size $Wc_c fi # ============= README ============== echo "x - extracting README (Text)" sed 's/^X//' << 'SHAR_EOF' > README && Xuntype1 - Adobe Type 1 Font Decryption X XChris B. Sears XDigital Equipment, WSE XMay 31, 1990 X XThese utilities decrypt an Adobe Type 1 font and leave a raw PostScript file as Xa result. Most of this procedure is documented in "Adobe Type 1 Font Format" Xavailable from Adobe Systems. X XConverting a Type 1 font program into the outlines is done in two phases. XIt assumes that you have a Macintosh, a Unix system and Display Postscript. XI haven't tried using NeWS, GhostScript or a LaserWriter, but they'd probably Xwork as well. The PostScript that I use is pretty simple, but the Ximplementation limits of other systems may break this. X X1. Using un-adobe, which is in hqx format, convert the Type 1 font into X a eexec encoded text file. Un-adobe.hqx was snarfed off of SUMEX. X I can't remember who wrote it but you can find that out when you run X the program. X2. Using untype1, a shell script driver, convert the results into a list X of simple PostScript programs. X XHere is a description of the files in this directory: X X untype1: a shell script that uses eexec, chars and DPStest to take X an ASCII PostScript PostScript file with an encrypted Adobe Type 1 X font and generate raw PostScript for the font X Makefile: a make(1) description file for compiling exec.c and chars.c X eexec.c: decrypts a font file encrypted for the eexec operator X chars.c: decrypts a font file of encrypted CharStrings. chars couldn't X easily be written to accept standard input because it repositions X itself with fseek() after a charstring has been decrypted. X header.ps: a PostScript wrapper that removes font hints, squashes X procedures and transforms operators and operands X trailer.ps: a PostScript wrapper to send the filtered PostScript to the X standard output X un-adobe.hqx: a Macintosh application that converts an Adobe PostScript X font into an ASCII file for transfer to a UNIX system X view_pre.ps and view_post.ps: After converting a Type-1 file, these X files can be used for viewing the results with Display PostScript. X XTo decrypt a Type 1 font first transform the Adobe font file into a text file Xon a Macintosh. This can be done with the Macintosh program in unadobe.hqx Xwritten by Jerry Keough and Ted Ede at Mitre Corporation. Next transfer the Xencrypted PostScript file from the Macintosh to your UNIX system with a file Xtransfer utility like NCSA Telnet or Kermit. Be sure to transfer this file Xin text mode and *not* binary mode). Once the font file is on your UNIX Xsystem, you can perform the decryption with the shell script untype1. X Xuntype1 is basically three pass: it runs eexec and chars, wraps the output Xwith header.ps and trailer.ps and then runs it through Display PostScript. XTo interact with Display PostScript we use dpstest(1X) found in X/usr/examples/dps/dpstest in the Ultrix release. The result is a very simple XPostScript file containing only: X X /characterName X closepath X curveto X lineto X moveto X def X { } X Xview_pre.ps and view_post.ps are useful for displaying the font using XDisplay PostScript. Concatenate view_pre.ps, the font file and Xview_post.ps together. The results can be viewed with DPS. X XNovember 9, 1990 X XStoneSerif used " |- " rather than " RD " to read the encrypted charstrings. XI Added some notes to this document. XThere is a bug with seac where the x origin of accented characters is wrong. XRenamed the shell script transform to untype1. XThe header.ps and trailer.ps files were substantially revised to use the Xpathforall operator. This resulted in much simple code and the resulting XPostScript output was much simpler still. Used bind def. Save those cycles. XYou may want to use flattenpath as well. SHAR_EOF $TOUCH -am 1114180290 README && chmod 0644 README || echo "restore of README failed" set `wc -c README`;Wc_c=$1 if test "$Wc_c" != "3658"; then echo original size 3658, current size $Wc_c fi # ============= chars.c ============== echo "x - extracting chars.c (Text)" sed 's/^X//' << 'SHAR_EOF' > chars.c && X/* X * chars.c -- decrypt an Adobe font file of encrypted CharStrings X * X * Chris B. Sears X */ X#include <stdio.h> X#include <strings.h> X X#define TRUE 1 X#define FALSE 0 X Xint lenIV = 4; /* CharString salt length */ X Xtypedef struct { X char *command; X int value; X} Command; X XCommand commands[] = { X { "notdefined_c0", 0 }, X { "hstem", 1 }, X { "notdefined_c2", 2 }, X { "vstem", 3 }, X { "vmoveto", 4 }, X { "chars_rlineto", 5 }, X { "hlineto", 6 }, X { "vlineto", 7 }, X { "rrcurveto", 8 }, X { "chars_closepath",9 }, X { "callsubr", 10 }, X { "return", 11 }, X { "escape", 12 }, X { "hsbw", 13 }, X { "endchar", 14 }, X { "notdefined_c15", 15 }, X { "notdefined_c16", 16 }, X { "notdefined_c17", 17 }, X { "notdefined_c18", 18 }, X { "notdefined_c19", 19 }, X { "notdefined_c20", 20 }, X { "chars_rmoveto", 21 }, X { "hmoveto", 22 }, X { "notdefined_c23", 23 }, X { "notdefined_c24", 24 }, X { "notdefined_c25", 25 }, X { "notdefined_c26", 26 }, X { "notdefined_c27", 27 }, X { "notdefined_c28", 28 }, X { "notdefined_c29", 29 }, X { "vhcurveto", 30 }, X { "hvcurveto", 31 } X}; X XCommand escapes[] = { X { "dotsection", 0 }, X { "vstem3", 1 }, X { "hstem3", 2 }, X { "notdefined_e3", 3 }, X { "notdefined_e4", 4 }, X { "notdefined_e5", 5 }, X { "seac", 6 }, X { "sbw", 7 }, X { "notdefined_e8", 8 }, X { "notdefined_e9", 9 }, X { "notdefined_e10", 10 }, X { "notdefined_e11", 11 }, X { "chars_div", 12 }, X { "notdefined_e13", 13 }, X { "notdefined_e14", 14 }, X { "notdefined_e15", 15 }, X { "callothersubr", 16 }, X { "chars_pop", 17 }, X { "notdefined_e18", 18 }, X { "notdefined_e19", 19 }, X { "notdefined_e20", 20 }, X { "notdefined_e21", 21 }, X { "notdefined_e22", 22 }, X { "notdefined_e23", 23 }, X { "notdefined_e24", 24 }, X { "notdefined_e25", 25 }, X { "notdefined_e26", 26 }, X { "notdefined_e27", 27 }, X { "notdefined_e28", 28 }, X { "notdefined_e29", 29 }, X { "notdefined_e30", 30 }, X { "notdefined_e31", 31 }, X { "notdefined_e32", 32 }, X { "setcurrentpoint",33 } X}; X X#define MAX_ESCAPE 33 X X#define CR 4330 X#define CC1 52845 X#define CC2 22719 X Xunsigned short int cr, cc1, cc2; X Xunsigned char XDeCrypt(cipher) X unsigned char cipher; X{ X unsigned char plain; X X plain = (cipher ^ (cr >> 8)); X cr = (cipher + cr) * cc1 + cc2; X X return plain; X} X Xvoid Xmain(argc, argv) X int argc; X char **argv; X{ X FILE *in, *out; X unsigned char in_buff[BUFSIZ], byte, *rd_pos, *count_pos; X int in_size, line_pos, i, count; X long value; X X if (argc != 3) { X fprintf(stderr, "Usage: %s input output\n", argv[0]); X exit(0); X } X X if ((in = fopen(argv[1], "r")) == NULL) { X fprintf(stderr, "%s: can't open %s\n", argv[0], argv[1]); X exit(0); X } X X out = fopen(argv[2], "w"); X X setbuf(out, NULL); X X /* X * TODO: rewrite this so as not to use a seek and to use stdin. X */ X for (;;) { X line_pos = ftell(in); X X if (fgets(in_buff, BUFSIZ, in) == NULL) X break; X in_size = strlen(in_buff) - 1; X X if (strncmp("/lenIV", in_buff, 6) == 0) X lenIV = atoi(in_buff + 7); X X if ((rd_pos = (unsigned char *) strstr(in_buff, " RD ")) == NULL) { X if ((rd_pos = (unsigned char *) strstr(in_buff, " -| ")) == NULL) { X fputs(in_buff, out); X continue; X } X } X X /* X * We found an encrypted CharString. X * Back up and determine the number of encrypted characters. X * These have the form: dup 105 9 RD 9bytesofdata noaccess put X */ X for (count_pos = rd_pos - 1; X (count_pos >= in_buff) && (*count_pos != ' '); X count_pos--) X ; X X if (*count_pos == ' ') /* This can be at the beginning of a line */ X count_pos++; X X /* X * Write out the beginning of the string without the RD stuff. X */ X fwrite(in_buff, count_pos - in_buff, 1, out); X fprintf(out, "{"); X X count = atoi(count_pos); X X /* X * Seek to and read the binary data. X */ X fseek(in, line_pos + (rd_pos - in_buff) + 4, SEEK_SET); X fread(in_buff, BUFSIZ, 1, in); X X /* X * We must restart the decryption machinery for each CharString. X */ X cr = CR; X cc1 = CC1; X cc2 = CC2; X X /* X * Skip over the salt. X */ X for (i = 0; i < lenIV; i++) X byte = DeCrypt(in_buff[i]); X X /* X * Translate the buffer. X */ X for (; i < count;) { X byte = DeCrypt(in_buff[i++]); X if (byte == 11) { /* return */ X fprintf(out, " %s", commands[byte].command); X break; X } else if (byte == 12) { /* escape */ X byte = DeCrypt(in_buff[i++]); X if (byte > MAX_ESCAPE) X fprintf(out, " not_defined_e%d", byte); X else X fprintf(out, " %s", escapes[byte].command); X continue; X } else if (byte < 32) X fprintf(out, " %s", commands[byte].command); X X if (byte >= 32) { X if (byte <= 246) X fprintf(out, " %d", byte - 139); X else if ((byte >= 247) && (byte <= 250)) X fprintf(out, " %d", X (byte - 247) * 256 + DeCrypt(in_buff[i++]) + 108); X else if ((byte >= 251) && (byte <= 254)) X fprintf(out, " %d", X -(byte - 251) * 256 - DeCrypt(in_buff[i++]) - 108); X else if (byte == 255) { X value = DeCrypt(in_buff[i++]); X value <<= 8; X value += DeCrypt(in_buff[i++]); X value <<= 8; X value += DeCrypt(in_buff[i++]); X value <<= 8; X value += DeCrypt(in_buff[i++]); X fprintf(out, " %d", value); X } X } X } X X fprintf(out, " }"); X X /* X * Seek just past the CharString bytes and continue. X */ X fseek(in, line_pos + (rd_pos - in_buff) + 4 + i, SEEK_SET); X } X X fclose(in); X fclose(out); X X exit(0); X} SHAR_EOF $TOUCH -am 1109112490 chars.c && chmod 0644 chars.c || echo "restore of chars.c failed" set `wc -c chars.c`;Wc_c=$1 if test "$Wc_c" != "5322"; then echo original size 5322, current size $Wc_c fi # ============= eexec.c ============== echo "x - extracting eexec.c (Text)" sed 's/^X//' << 'SHAR_EOF' > eexec.c && X/* X * eexec.c -- decrypt an Adobe font file encrypted for eexec X * X * Chris B. Sears X */ X#include <stdio.h> X#include <strings.h> X X#define TRUE 1 X#define FALSE 0 X X#define EEXEC_SKIP_BYTES 4 X Xunsigned short int er = 55665; Xunsigned short int ec1 = 52845; Xunsigned short int ec2 = 22719; X Xunsigned char XDeCrypt(ch1, ch2) X unsigned char ch1, ch2; X{ X unsigned char plain, cipher; X X /* X * Decode hex. X */ X if ('A' <= ch1 && ch1 <= 'F') X ch1 -= 'A' - 10; X else if ('a' <= ch1 && ch1 <= 'f') X ch1 -= 'a' - 10; X else X ch1 -= '0'; X X if ('A' <= ch2 && ch2 <= 'F') X ch2 -= 'A' - 10; X else if ('a' <= ch2 && ch2 <= 'f') X ch2 -= 'a' - 10; X else X ch2 -= '0'; X X /* X * Decode cipher. X */ X cipher = ch1 * 16 + ch2; X X plain = (cipher ^ (er >> 8)); X er = (cipher + er) * ec1 + ec2; X X return plain; X} X Xvoid Xmain(argc, argv) X int argc; X char **argv; X{ X FILE *in; X char in_buff[BUFSIZ], out_buff[BUFSIZ]; X int i, o, in_size; X int skip_salt = TRUE; X X if (argc != 2) { X fprintf(stderr, "Usage: %s input\n", argv[0]); X exit(0); X } X X if ((in = fopen(argv[1], "r")) == NULL) { X fprintf(stderr, "%s: can't open %s\n", argv[0], argv[1]); X exit(0); X } X X /* X * Just copy to output until we see an eexec. X */ X while (fgets(in_buff, BUFSIZ, in) != NULL) { X if (strcmp(in_buff, "currentfile eexec\n") == 0) X break; X fprintf(stdout, "%s", in_buff); X } X X for (;;) { X if (fgets(in_buff, BUFSIZ, in) == NULL) X break; X in_size = strlen(in_buff) - 1; X X /* X * Decrypt a line of hex. X */ X for (i = o = 0; i < in_size; i += 2) X out_buff[o++] = DeCrypt(in_buff[i], in_buff[i + 1]); X X /* X * Skip the salt if this is the first cypher line. X */ X if (skip_salt) { X fwrite(out_buff + EEXEC_SKIP_BYTES, o - EEXEC_SKIP_BYTES, 1, stdout); X skip_salt = FALSE; X } else X fwrite(out_buff, o, 1, stdout); X } X X fclose(in); X X exit(0); X} SHAR_EOF $TOUCH -am 0601103390 eexec.c && chmod 0666 eexec.c || echo "restore of eexec.c failed" set `wc -c eexec.c`;Wc_c=$1 if test "$Wc_c" != "1829"; then echo original size 1829, current size $Wc_c fi # ============= header.ps ============== echo "x - extracting header.ps (Text)" sed 's/^X//' << 'SHAR_EOF' > header.ps && X%! X% X% header.ps X% X% After interpreting a decrypted Adobe font program there are four dictionaries. X% X% font (implicit) X% FontInfo X% Private X% CharStrings X% X% The strategy is to redefine certain operators, interpret the font and dump X% the resulting dictionaries while filtering out font hint operators. X% The resulting paths are converted into very simple PostScript using X% the pathforall operator. X% X X/readonly { } bind def X/executeonly { } bind def X/noaccess { } bind def X/definefont { } bind def X X/clearStack { X cleartomark mark X} bind def X X% X% commands for starting and finishing X% X/endchar { clearStack } bind def X X/seac { X /achar exch def X /bchar exch def X /ady exch def X /adx exch def X /asb exch def X X /xOrigin adx def /yOrigin ady def X mark Encoding achar get load exec pop clearStack X /xOrigin 0 def /yOrigin 0 def X mark Encoding bchar get load exec pop X} bind def X X/hsbw { X pop /xOrigin exch xOrigin add def X xOrigin yOrigin moveto clearStack X} bind def X X/sbw { X pop pop /yOrigin exch yOrigin add def X /xOrigin exch xOrigin add def X xOrigin yOrigin moveto clearStack X} bind def X X% X% path construction commands X% X% convert the operators and operands to rmoveto, rlineto and rcurveto. X% chars_closepath has different semantics from PostScript closepath. X% X/chars_closepath { X currentpoint closepath moveto clearStack X} bind def X X/hlineto { 0 rlineto clearStack } bind def X/hmoveto { 0 rmoveto clearStack } bind def X/chars_rlineto { rlineto clearStack } bind def X/chars_rmoveto { rmoveto clearStack } bind def X/vlineto { 0 exch rlineto clearStack } bind def X/vmoveto { 0 exch rmoveto clearStack } bind def X X/hvcurveto { X /dy3 exch def /dy2 exch def /dx2 exch def /dx1 exch def X dx1 0 dx2 dy2 0 dy3 rrcurveto X} bind def X X/vhcurveto { X /dx3 exch def /dy2 exch def /dx2 exch def /dy1 exch def X 0 dy1 dx2 dy2 dx3 0 rrcurveto X} bind def X X/rrcurveto { X /dy3 exch def /dx3 exch def X /dy2 exch def /dx2 exch def X /dy1 exch def /dx1 exch def X dx1 dy1 X dx1 dx2 add dy1 dy2 add X dx1 dx2 dx3 add add dy1 dy2 dy3 add add X rcurveto clearStack X} bind def X X% X% hint commands X% X/dotsection { clearStack } bind def X/hstem { clearStack } bind def X/hstem3 { clearStack } bind def X/vstem { clearStack } bind def X/vstem3 { clearStack } bind def X X% X% Arithmetic command X% X/chars_div { div } bind def X X% X% Subroutine commands X% All OtherSubr routines are hint related X% For 0, 1, 2 the stack contents are left unchanged. X% For 3, the trailing pop will push a 3 on the stack. X% See p. 95 of the Black Book. X% X/callothersubr { X} bind def X X/callsubr { X /i exch def X i 0 eq { X% pop pop pop % Flex height control parameter and end points X /yEnd exch def /xEnd exch def pop X X /y5 exch def /x5 exch def X /y4 exch def /x4 exch def X /y3 exch def /x3 exch def X /y2 exch def /x2 exch def X /y1 exch def /x1 exch def X /y0 exch def /x0 exch def X /yRef exch def /xRef exch def X X x0 xRef add y0 yRef add x1 y1 x2 y2 rrcurveto X x3 y3 x4 y4 x5 y5 rrcurveto X X% X% The Flex can be replaced by a lineto. X% X X /chars_rmoveto { rmoveto clearStack } def X } if X i 1 eq { X /chars_rmoveto { } def X } if X i 2 eq { } if % leave the arguments on the stack X i 3 eq { } if X i 3 gt { % normal subroutines X Subrs i get exec X } if X} bind def X X/return { } bind def X/chars_pop { 3 } bind def % transfers from PS stack to BuildChar stack X X% X% setcurrentpoint shouldn't appear in a charstring program X% SHAR_EOF $TOUCH -am 1114112390 header.ps && chmod 0644 header.ps || echo "restore of header.ps failed" set `wc -c header.ps`;Wc_c=$1 if test "$Wc_c" != "3369"; then echo original size 3369, current size $Wc_c fi # ============= trailer.ps ============== echo "x - extracting trailer.ps (Text)" sed 's/^X//' << 'SHAR_EOF' > trailer.ps && X%! X% X% trailer.ps X% X X/Helvetica findfont 20 scalefont setfont X/myString 20 string def X/numString 20 string def X X% X% All of the numbers being passed in are real equivalents of integers. X% Convert them back into ints before printing so that print doesn't X% append a ".0" X% X/printNumbers { X /ii exch def X ii 1 sub -1 0 { index cvi numString cvs print ( ) print } for X ii { pop } repeat X} def X X% X% Traverse the dictionaries and arrays. X% Xbegin XPrivate begin XCharStrings begin X100 dict begin X X100 100 moveto X XCharStrings { % name procedure X gsave X /xOrigin 0 def X /yOrigin 0 def X (/) print exch myString cvs print ( { ) print X mark exch X gsave newpath exec cleartomark X { 2 printNumbers (moveto ) print } X { 2 printNumbers (lineto ) print } X { 6 printNumbers (curveto ) print } X { (closepath ) print } pathforall X grestore X ( } def\n) print X grestore X 0 40 rmoveto X} forall X Xshowpage SHAR_EOF $TOUCH -am 1114105990 trailer.ps && chmod 0644 trailer.ps || echo "restore of trailer.ps failed" set `wc -c trailer.ps`;Wc_c=$1 if test "$Wc_c" != "895"; then echo original size 895, current size $Wc_c fi # ============= untype1 ============== echo "x - extracting untype1 (Text)" sed 's/^X//' << 'SHAR_EOF' > untype1 && X#!/bin/sh X# X# untype1 -- transform an Adobe Type 1 font file X# encrypted with eexec and CharStrings into raw PostScript X# X XPROGRAM=`basename $0` XTMP1=/tmp/$$.tr1 XTMP2=/tmp/$$.tr2 XTMP3=/tmp/$$.tr3 XTMP4=/tmp/$$.tr4 XTMP5=/tmp/$$.tr5 X Xtrap 'rm -f /tmp/$$.tr?; exit 0' 0 1 2 15 X Xcase $# in X2) ;; X*) echo "Usage: $PROGRAM \"Adobe Type 1 font file\" \"output file\"" X exit 1;; Xesac X Xeexec $1 > $TMP1 Xchars $TMP1 $TMP2 Xsed -e '/definefont/,$d' $TMP2 > $TMP3 Xcat header.ps $TMP3 trailer.ps > $TMP4 XDPS > $2 <<end-of-here X#$TMP4 Xend-of-here SHAR_EOF $TOUCH -am 1113130990 untype1 && chmod 0755 untype1 || echo "restore of untype1 failed" set `wc -c untype1`;Wc_c=$1 if test "$Wc_c" != "535"; then echo original size 535, current size $Wc_c fi # ============= un-adobe.hqx ============== echo "x - extracting un-adobe.hqx (Text)" sed 's/^X//' << 'SHAR_EOF' > un-adobe.hqx && XDate: Tue, 13 Mar 90 23:59:57 -0800 XFrom: C43MRP%AVIARY.gm@hac2arpa.hac.com XSubject: unAdobe.hqx X XunAdobe is an application that converts an Adobe type 1 font into printable XASCII characters that can be edited into a postscript document. Written by XJerry Keough and Ted Ede of the Mitre Corp. X XEnjoy! X XMark Probert XDelco Electronics X X(This file must be converted with BinHex 4.0) X X:#h9Z3@4[BQ8ZFfPd!&0*9#&6593K!3!!!"Ld!!!!!2rl8dP8)3!"!!!BY(*-BA8 X"!!!!!!!!!!)!"h9Z3@4[BQ8Y6'pRT3!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! X!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!%&38%a+5e4&)3#IZ*E*RlL@c!!!(Hi X!!!!!!!!B,J!!!!#eC`!!!!!!!!!!)T!!!!!%#!LJ!j+!(!i'0%83`)i"p`"!)4# X%J)%KBGb-+F1QB8%#*J#d+%!!dB%kES+3!(NMTS`!JN'J3''LC!Q9)L!#!J)!T#% X$3J&McUaj-bH!R6dp+QeBJFdRA*D5+HhJEJF"D!#D@%55KJbC-QimMKS)S&D!L4F XcEZcBm!3!G!i$E0RTN3KC+fF*&#LLTX`B1NUlN!"pNlF!%6PTl*44kTB"J&`!c#e Xe@qia!(Y,q3$J"k"2!#Td!fC!!`#"3#G@rU&c%SFeL,!-)%!!)j!!"Zd!6N#i+&d X&8!XJrpK9HI+M"6mK50`%e`f!!HJA!*cSNU"PaaGq4QkE%0+QRaAQcRhhC-!F3Hr XITE-mHE%E!4`"d+8c`#5pJTd@Ae5c9bhGJUrpUqPLJ4$X0IHDIK!8L)"d#1LJi([ XakF+!'2L9GL!k,8$4R"+ZP2C'3'$!!F9[`BN)5iF)I&KD#f%K%0a`a4fAA(!&-L" XG",TBKaf-aL(A"Mp+"0%12dL!J)!8J%3BJ5Fk'L%L0"dbJ"i$F-!#jBSp)3#'*J$ X@4dZAZP$J$'d!%,'"CJ(`8`5C1X6S)cp3a1L%G!CSFkC!DT)*!K+!-0#6!@4B!!d X3-1`!J!&1l!1!!2l`iJm`rU$cMc,r8$1T%ek!m!886cJ"$@Vq1-1DDbd1iBirm-$ XaJ`MB4)(-2rcmX"X$U#L5(!!2*1F20$r`F*SZ$[M4J4[q["-U(!"!i%+S2`#!#L, X$k3S2+Sc!`%-!N!"!mJ85`!6#Q3$0bTSX+T0)L`SKQ'Vka$X!+1!TU++f&XGVTCQ X+UUUXZJUVZ,6D'PDZa2,U+fl!8M"XXFFQZk`cc6iV,J6L5N#ZZHKQqX@kcEfEQML XMaY'$CNDSpM%!-[bMcXF"L"!FbX,miijk3T`b)cT)k$'!"am-h#X!!m$a$h4#R"" Xc+K2Jp`mjqj'$bK`lSp#"CJ2m)`kbbNSGVUmBe#`!0p,jSmh14M`YN!$89,YJ03! Xl-k#e*&hcXR-9BJG!YX*Rlkb!eR2UiSmR1mmKK0P6dbh1eFeTMDMHJZ`Xb0pc9cd XifVkUV8F!`(4YaXkEa0dii)4,(S!QA51ambZ-"qiii3R8(!!5AE1`FbkPPefhVkR XV!3$AHN2XDc0JDfikjj!!!e!l!+adMFA1[2[+51b#Selc89hMJ2c1d[JZqq-l$jq Xh2aC-Ikd)c*mHr2!L50H22F1P3JF%(bJ38!"+!("'3!5!i8l5U9#!U40e,2"%(A5 X!!`""B)BdX+%-$TL#AplJ"M+!J!aT#!-EhR!'(9K!!8P`J`$T3%!$PX%#$6"#'Z3 X`"`j#8))8e-%6U)#'-S#J#8QJJK4`-S3hb!%10J`$(G,!3"#%B3jcU%-EA1L'0i" X!$Q@B!`lG-)FdL-'!DD"$(JKS3a$3SB8JU--FA2J'-eJ4$@QBJ`rK!!FfT'%-1Z5 XK'ea!!aD'FBaP2'-DHrM')R,3$&@FJ`6,`!)#PS%M"%5L#qPJa$'m!3jjF)%&$U! X#%)#JNBp%`42G%!Bj6"'2FQL$$N'3!!Bh%0+(EJ""%+B`K#3NJBUCh'3"$kK)&EK X4M'%JSaR4Z--HSJ31B4M$'Q"*48pb-T4"%!0,bR##19L!"&G!$"hS!"B3L''+5LL X$(#`*JL@8i3ee1!-D31P!+T6"J8Ai5LYVL%M%D*1$U3""$(+!!a`iFiSXG#%-C8K X$'q*3$R0Fi`94ST*KZZ#I&J#!"))QR3)S!cArJ)Gd$Z!$)IP$"#p!!#VFJ!TrT%) X#UB""+TJaY$fJ!JT`#-!+J!#N(@LQ!855$Mm)JB3I3D'Pr-ME!-LJ"10!BAi!S%@ XdA#URR38J&F4S%J2Dm!pB'3'RKS$T5hmN"1N%!!0#-%i46"S!H[5$#M"S`9@P!)3 XG!1'UkRN"$cJe"5S8jkUT!-8+[Y!2+#LK&@h&+3eHS&8Sh)J#G'fVG##!#4"d"`S X[J%"BkbUG"rK#1[P!4PlYUJX)''+aU4M&@pYk"@!3i5K5MGmC01%QTmT"U6$0Q`" XF3CYrX-i,G,)!U%64XC&"`@8MZ`'0c-D1jl&"9k+J&`-LqMbcqNS!dP'!(l$`"0c X'E%DXRBiNULB+p`P%X`%K$fb%-"Z%k(CRTP81+b)UR36BJPi)J)%VrS'+G'fU8p" X!J![iZC+@"&3#U1N(1cUQ@hZPDP@YHP@XI*9G9#@R(`V943)qk`B!rpFGd[Q(%C6 XJ!J#E)5!')"-MSP9JH-LU(qi!,hFPT)FHX*8G5LJ`1ajm+$+KJ3(+UBCm58`##J2 Xi`[IM!9'+)0DEB)%+mK'!Kq9,*JkJq"r2@(&!*$!Fm2i!![+Kaij",')5Dm$&&Qj X`KPZdB3BJB-RQjC6'60Ba',9R4[19%!JmE$)[PfBrB@D!(mLX$M-[5%+5B,0jUB" XH8*'$[Q&4J(haP9pB84K9iN+!VX+m!%Kif"rZm,)rDNZX!$'!!)GqfAU@&D!'#!) XrrN$DXZi-,'@`*p25FB!6&-hS5,dQdi%0lT@rJ'K5bmF!N6Dc!h5&MP-M$FN#0NH XN2meT"dL!ep*T!!ZbA'FV"!3*ji#!)m-#!4(!TMa&d!F!@#!"$0KJB1R)!!8#)!! XKi%S#mXK*&*Ea$hP-!4"Q-!F6[N'!"9RX'jb*VUGJ%!-Cc)!'0E$"$A#3!)-J#'% X)4#L#%4$+0RQj&VDDN5dl@X!(*PaKi2q3!!5DR`H&Q2Pd4T)iVR+5#`%&-0Hjm*0 XIG(9,h4jIPlmcfZkE$q!"m)UA[-6fP%!0!!4m!#%9b3""FFq"!3#B`!%S3%!B$," XZ!'#!IbpB!!PDm!pCQ!%NAq$IGQia$$%3i"E%%)-"5,!#%+R$U8K33YF0F!B)"%% XI!B!$$&BKd,-(!!a1*3$A!b)G!("!#B)!!c'J!i)&!!-A!p$!#BJULi#-Y1NJq!$ X58lB!B3"H!d0S"q)M8(CB"1)-""!"%-"!$a!!3353!"#"iZYJ,AVB!1GK8-!CJ%Y Xk(Y$M"MK(0K!!!3+Qbk,X)QMmiber"JGi(J33-)-peXeYC2'2q!))+G)4X+jr1%- X)VfM1#`ibd!m0k%-D#-)k!'#"kGYGjk!!`!dqe(-#B%`'QP)#%-kJ!6rpSaT29hi XGh*q1"rY$(Q)(!18"i!pe',m1%G9mcaGpZd9p3Q"p"`J!'J"qc-FZk2F&kRF'$1" Xqd'"rZL"rraH!lq"md#Gp"SL!f!Gq#A"qkEGq#&"6rk!+mq-2KX!rq4F"CL!#!YL X"$2!$D`!!"'"di"F!jaH"*mKd+XKrA-!r#F!%8`!&hY3'b)+$-H!#-K!%!$!&4!8 X1*V8Srq!0h2%2f#!%VG"d@DJ+*J8$-!"cZX!6GBF&G3F+6L9UZK!!%X!#6@!#%2J X"Cd!#GJ!!0Y!#!!!#iE!%,I93%e94&j94'p941KF*``!+,H"8j6-0BA"8#V!'%'" X5rj!!$rp32(9!LIG`LIb6KCJB"LT3GQ[!!CVi$kj!LIM`$l$!2j4SLDI)"rqJ$kV XBL86P#PQiLR8!!6JJ!!GJ"KDJL`)3#@T!!2rh%VJb"3"J"[6J-r`MIdI3$[S!!N, X3G3H!!0Xh%!G`!CVa%K%!"G[R!&'`I3EJMFd4MJ$3!%,!GJK`!pX)!"5JMHHB,1C XM#Xpi$ri`M3"3MGXA%0Q)*[T(MZ!SMZE)!1D)MZV)MS[LM[$B!2+S#rhJ"[`6!jc X4!!UJ"*hBKD6!2e!JHDT3HdeR"JV!K8dA"4bC#[4J!N$30@L3!(pNChEki!q3!," XfEIH5J0!e*!!#A3F!B#!05V#,MU!'MB3(!3!$3i!2!8!"4J)*N8!($!!,J["")K! X&)B!-4bN#J#!%%5!#H#!!UL!#L!!#JK!0UC!!-A8!#Q2!2`63K%m)!-J'$-!!!Y" X"!4"PG#r`)4$JMQ%`Dq`b%"L`EJ-`!-6&2mJ'!`"!!Q`T"-83$#D`1N0`$-"J$FJ Xa"2mQ$)mC##!`!%9R)hA3PX!`Pa4`"N)!Ph4TPhMT)&$BPpr`Pi'jQHIJPTjj"Si X%(4J3"KkJ")!`M0!3IAM9%aK3PmRLMRi*Q*e5"mJ5#-#!E$i!!#S!!'SJ!%3!##` X3!-e*")&JQ)XT"&FC#(M`!H-J#H-!#H13!!L`-!KY3!#3!$!)8K!)8d!%E1!15P! X)d`N)Zf!)daN)4FF(D+Q@8"K4I2FK9,+(EaQJ)##J"*TiQZ)#Rb#BV8PlGSNX!rU XJ"9UJGJN$F5N((f!15#!*K"+A!Y!6"a!!m(#Aa$F!,h!&Km)&`iPXm-#J4ZHJ%3U XK-%TqG2!"&'Th'%S*3'#K0HS"'+UK-#!!B$#1m"!3A!8,3I!'pV#M(CU2G[!2iE! X#a`!$G`N("b!$d-%"!J#&"`!*3G#Ni!#P-*!!%m6h!#9D'PV'QZ$!SK5JSp#K!6d X+"-J#"LG)Q-N)"88D"'f`M!F`9`VBEIN)#8*!"rm!$LTJ"!)!!9)+!-!J!'B!!fa XUG'm+!fpR!%T!TfE!!9cP*`$`!@mJ$c@+!8Yk!))D$S9kU)QkU-4h!%"`$Vlj%JT X!"0p`TQh*SSKDS4HDS4[UMU(UQiiK!8-TSYm3!!1!SJVUPL$`)A**IR*`!##3!!' X"J!P4N!!-X4LFCBS!XYUDEiQX)U#Xc*S"`3#YdUS2e'ULeTULf(UXlVLY4VHXc@S X%J2#YdIS2q$#ZCQUZi!!-RiUZ'U#Z(Z#E&!!!(M!SKA)SLC+3!)lK'!hK!3$J!P3 Xk#iKJ"IVPP`H!-Hj#R!FJ!KK!!KNJ#))J#i)!XIpJ$f"J$P5+X4T,#)&!#i%!XL* XV$CaTTHk)VKBJ!NL!,#,3Q6KlXcUEXjf*I9-3"'IJ!A$`!9`U$NN3"%-+!$#3!!h XabJrdUJ!8bcm4N!!&Q`S'YA81pkUZ')#Z(1#[GNFe'%!$!T8"K8F'!V"Y8m!G#$! X,#'!&P-)2CL!!K5Ha82!)5+F!kSS!*1#I03S"BLX"'L!,!Q#ffbB"`J!'!L!"fK! X&E`X,!8!#Ak!Zl1)Zd$#Vk2TVrLP39!-"-!X"2cX&31!5A$ULA'#h!+J!k1SHbB) X"FJ!!kXS!J%%"'3!,h(&-5#!&Sm3G%$!,#Z#fX()'4i)%S!X'hY#kN!#V+CcL!i% X`Ep""!%2!,JBJ!`"3$NNJ$F%!!P%J!TH!E!!!$UdV"8J!"KT!!MVNMKSJ$B2,!*3 X3!&13!(`!)!IrJ,J3X,K[UbrNX'i(N!!XJH!#5B#l)(!&RN)#02S"E1#q-[!"EX! X!4"!%Z-ZP"B`XFK!!QL)#9r!#!K#l%!!0`5!&3N!*39$!J%'lEb!!2bS"`)#i%Y" XR-98()dV"E3QRb3)"+D`[r#$!-%$!"Sc!#Xc!3H$!lK["QQ,"'1c"(2`''#$#*"b X-%)#M'M`%55Zr62Zfr*0i"i`%35!$r#8#NIXK""#l%3!"83`V@[brB%!!e-U@2!F X$H!!!9*-"''`$!!#CYR#N"'!$!B!(r`!"Jf$&3H)'!K$"2bX,"bJ!-L!!Z&X%m## XT4a#L!8!$#f!#5Q!*`%!*5d!%h'%!&6!#M!XVL(bAPX$!3f!,32!'"J$(L%X"6%Y XZr#!&4,"Z$("dG4!&`B#i8"!-#18-3H!1cKF#,E+(-F"X4ZGXc4%#89#B3N!D,#! X%U,#`5K!!6`F+3#S!S$!!2G!6%L$-$#!#bi`#Q+,&m%B3lK)0#!8-ZI`2`-$,[bN X"[qb1h(I-GJF+"e$0h)I0-V$-&J!#++#dD5S1J!!-F1%$i`!)i3!)`S`!9YR0Ar$ X0!5&UiT`Dj+c,j``E!J8+&#$2cGBLpFap#&fh6Y$3jPc1%GdZ!VA1TQ%"S&!"mLa XUAU$&TG[4i`c5*-epk1`q%J!+%j!!dJMGdKjYT,S-#qJX!5-0c!15caS!#LF)",l XScK`!#Z5"!%-!&b!J!Zj3'L)3*D$3!2+X@LZGd2%'!!apbqAX$1MX!%(G(1e-e%+ X3!-mES-c[l,SB[F`B)-r`p@jG6EPJVF[1X-k1J3'J%0Fpi3!&VFd,Qp0fkp'iM0I XV60BBS0I6KXkQi3+J3!3@[G'&IGI1apKm(3%T(GM,c!'%lG+TFGLA,G%Bi0M[,!% Xi[G8kEGPjhFYm(3$bl#i@3`9fqbQT`G1U10CPl4K$VB"+cG4b(343AG$@NLbJi!) X)VG$Y!YUU@-iq(4CNVFi5hGXDm0X-m04lk(+q!J((lGaA,GI*AGI-,GTL$GflIGB X+D0T,[3$J[GA+(FkX2G0PAG*TVB#JN!!!UFh5K3d+`iCfR$$'A`!+!)afS4Hj6`! X+'H!0R#&UD#F)!+k)6S"fH!!+0K$K!8!(SD!"hNF!&Ui'$li"&Zi&,l#9$-(KD-F X&)mk91'MK8M$'(a!+)Z!#L'$K2[$J)f$K02$J*H!#YfN!3R!*&Ni#&Zi",UiTS#$ XND#HANIX&S@!#-QlK"VhNSB!#6bjYqP$N!Ai#%3i!m1$LSH!"93i!j2$JLLGYf[$ XJ)F$MDZ$M3#jY"b9Ya)$PS!!#@ki,!"i+5"$QVJ!+AGX6*Nim@K`+(5!##+!T),# Xr05PYNZ$LS-!%2,lPKX$S+5PYIX$S6E$PG2$J+l$P(VlNS*!!!PX1"JqZ!PYZ"3q XH"&[1"!pZNG)Q"!qq"&Z1!b-q!2R-iA8JHSRhi#iJ!N'`jA!TP+Eajal`!eZC%lB XqiN1jiY,fRbq3!!!aX+Kd6T`k1AbT#3#mG3iIi!-J%!&r&hKQB!"`-!NGMJ**J!$ XrHJ"RB!$@mJq,B$mX)*3BB!*KiES4i(L"aqY4N!!))T!!!J&KlaVJ!J%3"BH!,0- X3$,1`$'43'dV!lr)$!@SJ%#SJ!QQ!Jp2J$%S3!6FB!%6q!##`PDSJ#F[-a[p!!Vk X#J`$JX@dJ%!C!!0i'#*)J#!J3#!(a#F(J#C`K!5U`(P"Bk&33"8M`!U4"%#"!!Gf XZiH2a!963N!!!i!e+)!&Q`!)LX*al'2#!!!Q(i%,!b`#K`3!I"!*8)!*+82!JF!# X6!!b4B08Z!!*-S&CJB!HD8AIQi&6FA)DJ%28"8AXi+#3#"IB&ArEF!!KRhac(V35 X(J&0+!!)*!!Q+`(iL!!"4%!L5F281N!$e-KpGC8!!AJm'TP!#5F%%dD#d0ik$)f! X%!6%"QT%8c9jh,9L'b&"hRlFYR`m$B!#YL4!&8B,iLSpjR"m3**!!"#63$RI2"*( XJ$#5!$#LJ#"J3I4#!,0r!,JLJi!+eERb!$mmZ!0%qp'HJ!%A[H6jIaVN-!$QHc`$ XJldSJrK+S"R**'J43m4Hr"JT!!NJ3$F%3#mY3"Yi3T,%!r!``"JT9"hL2!,$J%,3 X"khF!)Sp!mAV4i"K%!Q$J#3$"5-&"MHqiUEfapm`fRIq$!Mk2!SJr+!!)3N"5L!$ XH"J"%Jh-'K3$!0)J58maAd)9'acrSJ!6l!Mm!2L#!9U!1k-!!L($rJ"l3!H!LLp` X"(6"aUN(S%33kK3#-d@qkHfB)q*'k1&!!l)"2539*Db!8&Ap`&(K'&43!J1!4r!0 X"-(X@"3Mi"9)$!Z`%!4$crS%j)!!l33%)J%rJ$bE!2pJ*L'm3q!-JN!!!GJ)J5!# Xr)"`)$d!J!!4!!MJ%p-!!e%%%S!$`S!bVJe%Y!A`#)1!(kZ"15!#G)#!N!%%J#@R X"!I!(#3!4&-(%&`(%33+BFhi3'!`"IH!)rH!ri"RjJ#l)MD,##PZK+hb&X$!@bX* XC5!YVS5fmKEL`&Vk2J2!2U1!Uj"Q!B!!!J[a&14c!!!J%i)!$()"K!!p`J!-i"lJ X!$RL!1m!"`)%2d!%1!"Mi!@8)+BaK-2!(4f!!$!0r-!B'`6(`"h&J'$`$I`!'aX% Xj*!*cB"`kJ((`$6r!-)!82f!3D--r-!#!J5r`!`-J((J$2R!!jS!c`!-1i!FB!MM X!!6l!!!!(cT!!FP#TS`!1K#(P@)8lSDJX"B+`K2j!8F%((P&HK853!2J44k**,)N XIN4@QST5)%N9L5b5*,M%Q`X5CH"*PBNfNL5pa*'l%T8!#CJa"#!"*B!JiJ4%J%(D XK3!J!!F!)c"$54aDD)P)N#'kJ$E#ABG*(RSRAqbBJ)*bi%"-!!U,*0*NLeJ5ED"0 XmeJ6#3#GK!p"%QPL5&*!!pXK*(M!RD!#G["1[KdAQb3`"!6ANKZ53!&Ub4N3*'f! X$4b30R"-aJN5fL"a3$'4J0r!MSF!%P-)"X$&*Mb`8aB"J%"##3J!!$+%2!J%")!m X)!JI!M$KS#$b"J&-898"3()T&83JdP9C'%,5!6``)CN!T#TbLf,T@SGJL#!,!"KJ X#A[J2FN)'B![[iaF#J!`!#4D&$4!%8[!8+L"+d"#5Bd$B!*M!12S"h[JFJ8&c"!! XDdHj)Vp`i1B3M"qJ"$3&4I`!!: SHAR_EOF $TOUCH -am 0604153590 un-adobe.hqx && chmod 0644 un-adobe.hqx || echo "restore of un-adobe.hqx failed" set `wc -c un-adobe.hqx`;Wc_c=$1 if test "$Wc_c" != "9054"; then echo original size 9054, current size $Wc_c fi # ============= view_pre.ps ============== echo "x - extracting view_pre.ps (Text)" sed 's/^X//' << 'SHAR_EOF' > view_pre.ps && X%! X300 dict dup /font_dict exch def begin SHAR_EOF $TOUCH -am 0612145690 view_pre.ps && chmod 0644 view_pre.ps || echo "restore of view_pre.ps failed" set `wc -c view_pre.ps`;Wc_c=$1 if test "$Wc_c" != "42"; then echo original size 42, current size $Wc_c fi # ============= view_post.ps ============== echo "x - extracting view_post.ps (Text)" sed 's/^X//' << 'SHAR_EOF' > view_post.ps && Xend X X% X% The display order is strange because of the hashing of dictionary entries. X% X/myString 30 string def X/iChar 0 def X/Helvetica findfont 30 scalefont setfont X100 100 translate X Xfont_dict { % name procedure X /proc exch def X /name exch def X gsave X gsave X erasepage X 0.3 0.3 scale X gsave 0 0 moveto 0 1000 rlineto X 1000 0 rlineto 0 -1000 rlineto closepath stroke grestore X proc stroke X grestore X name myString cvs gsave 0 -50 moveto show grestore X gsave -50 -50 moveto iChar ( ) cvs show grestore X /iChar iChar 1 add def X usertime 800 add X { dup usertime lt { pop exit } if } loop X grestore X} forall SHAR_EOF $TOUCH -am 1113184090 view_post.ps && chmod 0644 view_post.ps || echo "restore of view_post.ps failed" set `wc -c view_post.ps`;Wc_c=$1 if test "$Wc_c" != "618"; then echo original size 618, current size $Wc_c fi exit 0