[comp.sources.atari.st] v01i001: uudecode.bas - starter version of uudecode in BASIC

koreth@ssyx.ucsc.edu (Steven Grimm) (03/21/88)

Submitted-by: wisner@eddie.MIT.EDU (Bill Wisner)
Posting-number: Volume 1, Issue 1
Archive-name: basic-uud

[This is a uudecode program written in ST BASIC and is revoltingly slow.
It should be used to decode the better, faster, compiled version called uud
that will follow in comp.binaries.atari.st. This version will only work
with files uuencoded by UNIX uuencode. ..b]

10    ' UUDECODE PROGRAM
11    ' /*
12    '  * Uudecode -- decode a uuencoded file back to binary form
13    '  *
14    '  * Slightly modified from a version posted to net.sources once;
15    '  * suitable for compilation on an IBM PC.
16    '  *
17    '  * modified for Lattice C on the ST - 11.05.86 by MSD
18    '  *
19    '  * rewritten for ST BASIC on the Atari ST - September 9, 1986,
20    '  *   by Patrick Simon
21    '  *
22    '  */

23    ' Initializations.
24    DIM I(4)
25    FULLW 2 : CLEARW 2 ' Use full output window, clear it.
26    MASK = 63 : SP = ASC(" ")

30    ' Get input filename and open file.
40    INPUT "Enter name of uuencoded file > ", IFILEN$
50    OPEN "I", #1, IFILEN$

60    ' Get output filename, open, and set up pointers.
70    INPUT "Enter name of output file > ", OFILEN$
80    OPEN "R", #2, OFILEN$, 45
90    FIELD #2, 45 AS CBUF$

110   ' Input and ignore first line of input file (original filename).
120   LINE INPUT #1, INLINE$ ' Due to a bug in ST BASIC, LINE INPUT #
130   LINE INPUT #1, INLINE$ '  must be called 2x, just to get first
140                          '  line. Even then we lose the 1st character.

150   ' Now set up screen for user.
160   CLEARW 2
170   GOTOXY 1,2 : PRINT "Decoding "; IFILEN$; " to "; OFILEN$
180   GOTOXY 1,4 : PRINT "# lines read in: "
190   GOTOXY 1,5 : PRINT "# bytes output: "

200   ' Initialize some variables for main body of program.
210   NUML = 0 : BYTEOUT = 0

211   ' [Comments removed from middle of loop to increase execution speed]
212   ' LINE INPUT should work OK by now!
213   ' (l. 231)  check to see if we are done yet
214   ' (general) For each line, must "decode" each byte.
215   '           First byte contains # bytes to ***output*** from this line.
216   '           Then, after decoding, each set of 4 input bytes contains 6*4 =
 24
217   '           bits of information to output, 8 bits per output byte, thus
218   '           3 output bytes.
219   ' (l. 260)  SPTR is string position pointer for INLINE$
220   ' (l. 280)  Get first byte = # bytes to output;
221   '           exit if line has zero to output
222   ' (l. 290)  Process one line of input
223   ' (l. 310)  Decode set of 4 input bytes.
224   ' (l. 410)  If more in this line, go back again.
225   ' (l. 420)  Finished processing line; ouput it; show status to user
226   ' (l. 450)  Get next line ...

228   LINELOOP: ' Now loop for as long as there are input lines.
230      LINE INPUT #1, INLINE$
231      IF INLINE$ = "end" THEN GOTO 500
232      NUML = NUML + 1

260      SPTR = 1

280      GOSUB DECODE : NN = C : N = NN : IF NN = 0 THEN GOTO 500

290      MPTR = 1
300      WHILE N > 0
310         FOR J = 1 TO 4
320            GOSUB DECODE : I(J) = C
330         NEXT J
340         C1 = ((I(1) *  4) MOD 256) + INT(I(2) / 16)
350         C2 = ((I(2) * 16) MOD 256) + INT(I(3) /  4)
360         C3 = ((I(3) * 64) MOD 256) + I(4)
370         IF N>0 THEN MID$(CBUF$,MPTR,1)=CHR$(C1) : MPTR = MPTR + 1
380         IF N>1 THEN MID$(CBUF$,MPTR,1)=CHR$(C2) : MPTR = MPTR + 1
390         IF N>2 THEN MID$(CBUF$,MPTR,1)=CHR$(C3) : MPTR = MPTR + 1
400         N = N - 3
410      WEND

420      PUT #2, NUML
430      BYTEOUT = BYTEOUT + NN
440      GOTOXY 20,4 : PRINT NUML
445      GOTOXY 20,5 : PRINT BYTEOUT
450   GOTO LINELOOP

500   ' Hopefully, we have now decoded the input file.
510   CLOSE #1 : CLOSE #2
520   END

999   ' Subroutine to decode a single character
1000  DECODE:
1010     IF LEN(MID$(INLINE$,SPTR)) = 0 THEN INLINE$ = INLINE$ + " "
1020     CH$ = MID$(INLINE$, SPTR, 1) : SPTR = SPTR + 1
1030     C = (ASC(CH$) - SP) AND MASK
1040  RETURN