/* XXENCODE REXX: Pipeline filter to xxencode */ Signal On Error Signal On Novalue Signal On Syntax Parse Arg file, /* File name to imbed. */ text . /* Keyword "TEXT" is allowed. */ /*-------------------------------------------------------------------*/ /* If the file is in text format, rather than binary, it will need */ /* to have its records delimited with line-feeds before the file is */ /* encoded, to preserve the record structure. It will also need to */ /* be converted from EBCDIC to ASCII before being encoded, so that */ /* the recipient gets ASCII when he decodes the file. */ /* */ /* Whether the file is binary or text, it needs to be blocked into */ /* 45-character chunks, each of which will become a 60-byte record */ /* after 3-to-4 expansion. */ /*-------------------------------------------------------------------*/ If Translate(text) == 'TEXT' /* ASCII translation wanted? */ Then blockit =, /* Yes, set up needed stages: */ 'block 45 c |', /* Block with line-feed. */ 'xlate 1-* e2a |' /* Translate to ASCII. */ Else blockit =, /* Translation not specified, */ 'fblock 45 |' /* so don't insert line-feed. */ /*-------------------------------------------------------------------*/ /* The following translate table is used to transliterate values */ /* between x'00' and x'3F' to printable characters that can go */ /* safely through gateways between ASCII and EBCDIC systems: */ /*-------------------------------------------------------------------*/ xxtable =, '00 + 01 - 02 0 03 1 04 2 05 3 06 4 07 5', '08 6 09 7 0A 8 0B 9 0C A 0D B 0E C 0F D', '10 E 11 F 12 G 13 H 14 I 15 J 16 K 17 L', '18 M 19 N 1A O 1B P 1C Q 1D R 1E S 1F T', '20 U 21 V 22 W 23 X 24 Y 25 Z 26 a 27 b', '28 c 29 d 2A e 2B f 2C g 2D h 2E i 2F j', '30 k 31 l 32 m 33 n 34 o 35 p 36 q 37 r', '38 s 39 t 3A u 3B v 3C w 3D x 3E y 3F z' /*-------------------------------------------------------------------*/ /* Each data record produced by xxencode (except for the last, which */ /* may be short) contains 45 characters from the input file. These */ /* are expanded to 60 printable characters. The first byte of each */ /* data record is a binary number specifying the number of input */ /* characters represented in the record. Thus, for 45-byte data */ /* records, the first character is (in EBCDIC) "h" (x'88'), which */ /* will become x'2D' when it goes through an EBCDIC-to-ASCII gateway.*/ /*-------------------------------------------------------------------*/ beginline = 'begin 0600' file /* Canonical xxencode header. */ 'CALLPIPE (endchar ? name XXENCODE)', '*: |', /* Read from pipeline. */ blockit, /* Reblock to 45-byte chunks. */ 'd: locate 45 |', /* Last record may be short. */ 'vchar 6 8 |', /* Recode, 3 bytes to 4. */ 'spec', /* Complete the formatting: */ '/h/ 1', /* record size (45 chars); */ '1-* 2 |', /* and expanded data. */ 'f: fanin |', /* Pick up last data record. */ 'xlate 1-*' xxtable '|', /* Make data printable EBCDIC. */ 'preface var beginline |', /* Prepend canonical header. */ 'append literal +|', /* Indicate end of data. */ 'append literal end|', /* Indicate end of file. */ '*:', /* Write to pipeline. */ '?', 'd: |', /* Process last data record: */ 'c: count bytes |', /* Calculate its size. */ 'copy |', /* (To unblock "count".) */ 'spec 1-* 1 x0000 next |', /* Compensate for "vchar". */ 'chop 45 |', /* Truncate compensation. */ 'vchar 6 8 |', /* Recode, 3 bytes to 4. */ 's: spec', /* Complete the formatting: */ 'select 1', /* get record size; */ '1-* d2c 1.1 right', /* make it one byte binary; */ 'select 0', /* get rest of record; and */ '1-* 2 |', /* put it next. */ 'f:', /* Send back to mainline. */ '? c: | s:' /* Count of bytes in last rec. */ Error: Exit RC*(RC<>12) /* RC = 0 if end-of-file. */ /*-------------------------------------------------------------------*/ /*-------------------------------------------------------------------*/ /* Error Subroutines */ /*-------------------------------------------------------------------*/ /*-------------------------------------------------------------------*/ Novalue: Say 'Novalue condition for symbol' Condition('D') 'on line' , Sigl':' Sourceline(Sigl) Address Command 'EXEC TELL MAINT AT PUCC Novalue Error'/* Phone home.*/ Exit 20 /* Exit with error setting. */ Syntax: Say 'Syntax error on line' Sigl':' Sourceline(Sigl) Say 'Error was:' Errortext(RC) Address Command 'EXEC TELL MAINT AT PUCC Syntax error'/* Phone home. */ Exit 24 /* Exit with error setting. */