Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

206 lines
7.5 KiB

  1. /*
  2. This file was derived from the libwww code, version 2.15, from CERN.
  3. A number of modifications have been made by Spyglass.
  4. eric@spyglass.com
  5. This file was removed from LibWWW and placed into the
  6. Security Protocol Module.
  7. jeff@spyglass.com
  8. */
  9. /* MODULE HTUU.c
  10. ** UUENCODE AND UUDECODE
  11. **
  12. ** ACKNOWLEDGEMENT:
  13. ** This code is taken from rpem distribution, and was originally
  14. ** written by Mark Riordan.
  15. **
  16. ** AUTHORS:
  17. ** MR Mark Riordan riordanmr@clvax1.cl.msu.edu
  18. ** AL Ari Luotonen luotonen@dxcern.cern.ch
  19. **
  20. ** HISTORY:
  21. ** Added as part of the WWW library and edited to conform
  22. ** with the WWW project coding standards by: AL 5 Aug 1993
  23. ** Originally written by: MR 12 Aug 1990
  24. ** Original header text:
  25. ** -------------------------------------------------------------
  26. ** File containing routines to convert a buffer
  27. ** of bytes to/from RFC 1113 printable encoding format.
  28. **
  29. ** This technique is similar to the familiar Unix uuencode
  30. ** format in that it maps 6 binary bits to one ASCII
  31. ** character (or more aptly, 3 binary bytes to 4 ASCII
  32. ** characters). However, RFC 1113 does not use the same
  33. ** mapping to printable characters as uuencode.
  34. **
  35. ** Mark Riordan 12 August 1990 and 17 Feb 1991.
  36. ** This code is hereby placed in the public domain.
  37. ** -------------------------------------------------------------
  38. **
  39. ** BUGS:
  40. **
  41. **
  42. */
  43. #define MAXCODE 64
  44. static const char six2pr[MAXCODE] =
  45. {
  46. 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M',
  47. 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z',
  48. 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm',
  49. 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z',
  50. '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '+', '/'
  51. };
  52. static unsigned char pr2six[256];
  53. /*--- function HTUU_encode -----------------------------------------------
  54. *
  55. * Encode a single line of binary data to a standard format that
  56. * uses only printing ASCII characters (but takes up 33% more bytes).
  57. *
  58. * Entry bufin points to a buffer of bytes.
  59. * nbytes is the number of bytes in that buffer.
  60. * This cannot be more than 48.
  61. * bufcoded points to an output buffer. Be sure that this
  62. * can hold at least 1 + 4*(nbytes+2)/3 characters.
  63. * outbufsize is the maximum number of bytes that
  64. * can fit in bufcoded.
  65. *
  66. * Exit bufcoded contains the coded line. The first 4*(nbytes+2)/3
  67. * bytes contain printing ASCII characters representing
  68. * those binary bytes. This may include one or two '='
  69. * characters used as padding at the end. The last
  70. * byte is a zero byte.
  71. *
  72. * Returns the number of ASCII characters in bufcoded or -1 in
  73. * the case of overflow.
  74. */
  75. int HTUU_encode(unsigned char *bufin, int nbytes, char *bufout, int bufoutsize)
  76. {
  77. /* ENC is the basic 1 character encoding function to make a char printing */
  78. #define ENC(c) six2pr[c]
  79. char *bufcoded = bufout;
  80. while (nbytes > 0)
  81. {
  82. if (bufoutsize < 4)
  83. return (-1);
  84. *(bufout++) = ENC(*bufin >> 2);
  85. *(bufout++) = nbytes > 1 ?
  86. ENC((*bufin << 4) & 060 | (bufin[1] >> 4) & 017) :
  87. ENC((*bufin << 4) & 060);
  88. *(bufout++) = nbytes > 2 ?
  89. ENC((bufin[1] << 2) & 074 | (bufin[2] >> 6) & 03) :
  90. nbytes > 1 ? ENC((bufin[1] << 2) & 074) : '=';
  91. *(bufout++) = nbytes > 2 ? ENC(bufin[2] & 077) : '=';
  92. bufoutsize -= 4;
  93. bufin += 3;
  94. nbytes -= 3;
  95. }
  96. if (bufoutsize > 0)
  97. *bufout = '\0';
  98. return (int)(bufout - bufcoded);
  99. }
  100. /*--- function HTUU_decode ------------------------------------------------
  101. *
  102. * Decode an ASCII-encoded buffer back to its original binary form.
  103. *
  104. * Entry bufcoded points to a uuencoded string. It is
  105. * terminated by any character not in
  106. * the printable character table six2pr, but
  107. * leading whitespace is stripped.
  108. * bufplain points to the output buffer; must be big
  109. * enough to hold the decoded string (generally
  110. * shorter than the encoded string) plus
  111. * as many as two extra bytes used during
  112. * the decoding process.
  113. * outbufsize is the maximum number of bytes that
  114. * can fit in bufplain.
  115. *
  116. * Exit Returns the number of binary bytes decoded.
  117. * bufplain contains these bytes.
  118. */
  119. int HTUU_decode(char *bufin, unsigned char *bufout, int bufoutsize)
  120. {
  121. /* single character decode */
  122. #define DEC(c) pr2six[(unsigned char) c]
  123. static int first = 1;
  124. int nbytesdecoded = 0, nbytes;
  125. unsigned char c, *pc;
  126. /* If this is the first call, initialize the mapping table.
  127. * This code should work even on non-ASCII machines.
  128. */
  129. if (first)
  130. {
  131. first = 0;
  132. memset(pr2six, MAXCODE, sizeof(pr2six));
  133. for (c = 0; c < MAXCODE; c++)
  134. DEC(six2pr[c]) = c;
  135. #if 0
  136. pr2six['A'] = 0; pr2six['B'] = 1; pr2six['C'] = 2; pr2six['D'] = 3;
  137. pr2six['E'] = 4; pr2six['F'] = 5; pr2six['G'] = 6; pr2six['H'] = 7;
  138. pr2six['I'] = 8; pr2six['J'] = 9; pr2six['K'] = 10; pr2six['L'] = 11;
  139. pr2six['M'] = 12; pr2six['N'] = 13; pr2six['O'] = 14; pr2six['P'] = 15;
  140. pr2six['Q'] = 16; pr2six['R'] = 17; pr2six['S'] = 18; pr2six['T'] = 19;
  141. pr2six['U'] = 20; pr2six['V'] = 21; pr2six['W'] = 22; pr2six['X'] = 23;
  142. pr2six['Y'] = 24; pr2six['Z'] = 25; pr2six['a'] = 26; pr2six['b'] = 27;
  143. pr2six['c'] = 28; pr2six['d'] = 29; pr2six['e'] = 30; pr2six['f'] = 31;
  144. pr2six['g'] = 32; pr2six['h'] = 33; pr2six['i'] = 34; pr2six['j'] = 35;
  145. pr2six['k'] = 36; pr2six['l'] = 37; pr2six['m'] = 38; pr2six['n'] = 39;
  146. pr2six['o'] = 40; pr2six['p'] = 41; pr2six['q'] = 42; pr2six['r'] = 43;
  147. pr2six['s'] = 44; pr2six['t'] = 45; pr2six['u'] = 46; pr2six['v'] = 47;
  148. pr2six['w'] = 48; pr2six['x'] = 49; pr2six['y'] = 50; pr2six['z'] = 51;
  149. pr2six['0'] = 52; pr2six['1'] = 53; pr2six['2'] = 54; pr2six['3'] = 55;
  150. pr2six['4'] = 56; pr2six['5'] = 57; pr2six['6'] = 58; pr2six['7'] = 59;
  151. pr2six['8'] = 60; pr2six['9'] = 61; pr2six['+'] = 62; pr2six['/'] = 63;
  152. #endif
  153. }
  154. /* Strip leading whitespace. */
  155. while (*bufin == ' ' || *bufin == '\t')
  156. bufin++;
  157. /* Figure out how many characters are in the input buffer. */
  158. for (pc = (unsigned char*)bufin; DEC(*pc) < MAXCODE; pc++);
  159. nbytes = (int)(pc - (unsigned char*)bufin);
  160. while (nbytes > 1)
  161. {
  162. if (bufoutsize < 3)
  163. return nbytesdecoded;
  164. *(bufout++) = DEC(*bufin) << 2 | DEC(bufin[1]) >> 4;
  165. *(bufout++) = DEC(bufin[1]) << 4 | DEC(bufin[2]) >> 2;
  166. *(bufout++) = nbytes > 2 ? (DEC(bufin[2]) << 6 | DEC(bufin[3])) : 0;
  167. bufoutsize -= 3;
  168. bufin += 4;
  169. nbytes -= 4;
  170. nbytesdecoded += 3;
  171. }
  172. if (nbytes < 0)
  173. nbytesdecoded += nbytes;
  174. return nbytesdecoded;
  175. }