rtsputil.cpp
上传用户:dangjiwu
上传日期:2013-07-19
资源大小:42019k
文件大小:19k
源码类别:

Symbian

开发平台:

Visual C++

  1. /* ***** BEGIN LICENSE BLOCK *****
  2.  * Source last modified: $Id: rtsputil.cpp,v 1.6.32.3 2004/07/09 01:48:16 hubbe Exp $
  3.  * 
  4.  * Portions Copyright (c) 1995-2004 RealNetworks, Inc. All Rights Reserved.
  5.  * 
  6.  * The contents of this file, and the files included with this file,
  7.  * are subject to the current version of the RealNetworks Public
  8.  * Source License (the "RPSL") available at
  9.  * http://www.helixcommunity.org/content/rpsl unless you have licensed
  10.  * the file under the current version of the RealNetworks Community
  11.  * Source License (the "RCSL") available at
  12.  * http://www.helixcommunity.org/content/rcsl, in which case the RCSL
  13.  * will apply. You may also obtain the license terms directly from
  14.  * RealNetworks.  You may not use this file except in compliance with
  15.  * the RPSL or, if you have a valid RCSL with RealNetworks applicable
  16.  * to this file, the RCSL.  Please see the applicable RPSL or RCSL for
  17.  * the rights, obligations and limitations governing use of the
  18.  * contents of the file.
  19.  * 
  20.  * Alternatively, the contents of this file may be used under the
  21.  * terms of the GNU General Public License Version 2 or later (the
  22.  * "GPL") in which case the provisions of the GPL are applicable
  23.  * instead of those above. If you wish to allow use of your version of
  24.  * this file only under the terms of the GPL, and not to allow others
  25.  * to use your version of this file under the terms of either the RPSL
  26.  * or RCSL, indicate your decision by deleting the provisions above
  27.  * and replace them with the notice and other provisions required by
  28.  * the GPL. If you do not delete the provisions above, a recipient may
  29.  * use your version of this file under the terms of any one of the
  30.  * RPSL, the RCSL or the GPL.
  31.  * 
  32.  * This file is part of the Helix DNA Technology. RealNetworks is the
  33.  * developer of the Original Code and owns the copyrights in the
  34.  * portions it created.
  35.  * 
  36.  * This file, and the files included with this file, is distributed
  37.  * and made available on an 'AS IS' basis, WITHOUT WARRANTY OF ANY
  38.  * KIND, EITHER EXPRESS OR IMPLIED, AND REALNETWORKS HEREBY DISCLAIMS
  39.  * ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES
  40.  * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET
  41.  * ENJOYMENT OR NON-INFRINGEMENT.
  42.  * 
  43.  * Technology Compatibility Kit Test Suite(s) Location:
  44.  *    http://www.helixcommunity.org/content/tck
  45.  * 
  46.  * Contributor(s):
  47.  * 
  48.  * ***** END LICENSE BLOCK ***** */
  49. #include "hxtypes.h"
  50. #include "hxstring.h"
  51. #include "dbcs.h"
  52. #include "rtsputil.h"
  53. #include "safestring.h"
  54. #include "hxheap.h"
  55. #ifdef _DEBUG
  56. #undef HX_THIS_FILE
  57. static const char HX_THIS_FILE[] = __FILE__;
  58. #endif
  59. /*
  60.  * Table for encoding base64
  61.  */
  62. static const char Base64[] =
  63.    "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
  64. /*
  65.  * Table for encoding URL-safe base64
  66.  */
  67. static const char URLBase64[] =
  68.    "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789!*";
  69. #define XX 127
  70. /*
  71.  * Table for decoding base64
  72.  */
  73. static const char Index64[256] = { /* Flawfinder: ignore */
  74.     XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,
  75.     XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,
  76.     XX,62,XX,XX, XX,XX,XX,XX, XX,XX,63,62, XX,XX,XX,63,
  77.     52,53,54,55, 56,57,58,59, 60,61,XX,XX, XX,XX,XX,XX,
  78.     XX, 0, 1, 2,  3, 4, 5, 6,  7, 8, 9,10, 11,12,13,14,
  79.     15,16,17,18, 19,20,21,22, 23,24,25,XX, XX,XX,XX,XX,
  80.     XX,26,27,28, 29,30,31,32, 33,34,35,36, 37,38,39,40,
  81.     41,42,43,44, 45,46,47,48, 49,50,51,XX, XX,XX,XX,XX,
  82.     XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,
  83.     XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,
  84.     XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,
  85.     XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,
  86.     XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,
  87.     XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,
  88.     XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,
  89.     XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX
  90. };
  91. #define CHAR64(c)  (Index64[(unsigned char)(c)])
  92. static void 
  93. Output64Chunk(int c1, int c2, int c3, int pads, char* pBuf,
  94.     INT32 bufOffset)
  95. {
  96.     pBuf[bufOffset++] = Base64[c1>>2];
  97.     pBuf[bufOffset++] = Base64[((c1 & 0x3)<< 4) | ((c2 & 0xF0) >> 4)];
  98.     if (pads == 2) 
  99.     {
  100.         pBuf[bufOffset++] = '=';
  101.         pBuf[bufOffset++] = '=';
  102.     }
  103.     else if (pads) 
  104.     {
  105.         pBuf[bufOffset++] = Base64[((c2 & 0xF) << 2) | ((c3 & 0xC0) >>6)];
  106.         pBuf[bufOffset++] = '=';
  107.     } 
  108.     else 
  109.     {
  110.         pBuf[bufOffset++] = Base64[((c2 & 0xF) << 2) | ((c3 & 0xC0) >>6)];
  111.         pBuf[bufOffset++] = Base64[c3 & 0x3F];
  112.     }
  113. }
  114. static void 
  115. OutputURL64Chunk(int c1, int c2, int c3, int pads, char* pBuf,
  116.     INT32 bufOffset)
  117. {
  118.     pBuf[bufOffset++] = URLBase64[c1>>2];
  119.     pBuf[bufOffset++] = URLBase64[((c1 & 0x3)<< 4) | ((c2 & 0xF0) >> 4)];
  120.     if (pads == 2) 
  121.     {
  122.         pBuf[bufOffset++] = '=';
  123.         pBuf[bufOffset++] = '=';
  124.     }
  125.     else if (pads) 
  126.     {
  127.         pBuf[bufOffset++] = URLBase64[((c2 & 0xF) << 2) | ((c3 & 0xC0) >>6)];
  128.         pBuf[bufOffset++] = '=';
  129.     } 
  130.     else 
  131.     {
  132.         pBuf[bufOffset++] = URLBase64[((c2 & 0xF) << 2) | ((c3 & 0xC0) >>6)];
  133.         pBuf[bufOffset++] = URLBase64[c3 & 0x3F];
  134.     }
  135. }
  136. INT32 
  137. BinTo64(const BYTE* pInBuf, INT32 len, char* pOutBuf)
  138. {
  139.     int c1, c2, c3;
  140.     //INT32 ct = 0;
  141.     //INT32 written = 0;
  142.     INT32 inOffset = 0;
  143.     INT32 outOffset = 0;
  144.     while(inOffset < len)
  145.     {
  146. c1 = pInBuf[inOffset++];
  147. if(inOffset == len)
  148. {
  149.     Output64Chunk(c1, 0, 0, 2, pOutBuf, outOffset);
  150.     outOffset += 4;
  151. }
  152. else
  153. {
  154.     c2 = pInBuf[inOffset++];
  155.     if(inOffset == len)
  156.     {
  157. Output64Chunk(c1, c2, 0, 1, pOutBuf, outOffset);
  158. outOffset += 4;
  159.     }
  160.     else
  161.     {
  162. c3 = pInBuf[inOffset++];
  163. Output64Chunk(c1, c2, c3, 0, pOutBuf, outOffset);
  164. outOffset += 4;
  165.     }
  166. }
  167. #if XXXBAB
  168. ct += 4;
  169. if(ct > 44) // EOL after 45 chars
  170. {
  171.     pOutBuf[outOffset++] = 'n';
  172.     written += 46;
  173.     ct = 0;
  174. }
  175. #endif
  176.     }
  177. #if XXXBAB
  178.     if(ct)
  179.     {
  180. pOutBuf[outOffset++] = 'n';
  181. ct++;
  182.     }
  183. #endif
  184.     pOutBuf[outOffset++] = '';
  185.     return outOffset;
  186. }
  187. INT32 
  188. BinToURL64(const BYTE* pInBuf, INT32 len, char* pOutBuf)
  189. {
  190.     int c1, c2, c3;
  191.     INT32 inOffset = 0;
  192.     INT32 outOffset = 0;
  193.     while(inOffset < len)
  194.     {
  195. c1 = pInBuf[inOffset++];
  196. if(inOffset == len)
  197. {
  198.     OutputURL64Chunk(c1, 0, 0, 2, pOutBuf, outOffset);
  199.     outOffset += 4;
  200. }
  201. else
  202. {
  203.     c2 = pInBuf[inOffset++];
  204.     if(inOffset == len)
  205.     {
  206. OutputURL64Chunk(c1, c2, 0, 1, pOutBuf, outOffset);
  207. outOffset += 4;
  208.     }
  209.     else
  210.     {
  211. c3 = pInBuf[inOffset++];
  212. OutputURL64Chunk(c1, c2, c3, 0, pOutBuf, outOffset);
  213. outOffset += 4;
  214.     }
  215. }
  216.     }
  217.     pOutBuf[outOffset++] = '';
  218.     return outOffset;
  219. }
  220. INT32
  221. BinFrom64(const char* pInBuf, INT32 len, BYTE* pOutBuf)
  222. {
  223.     int c1, c2, c3, c4;
  224.     INT32 offset = 0;
  225.     INT32 outOffset = 0;
  226.     while(offset < len)
  227.     {
  228. c1 = pInBuf[offset++];
  229. if(c1 != '=' && CHAR64(c1) == XX)
  230. {
  231.     continue;
  232. }
  233. else if (offset == len)
  234. {
  235.     /* BAD data */
  236.     return -1;
  237. }
  238. do
  239. {
  240.     c2 = pInBuf[offset++];
  241. while(offset < len && c2 != '=' && CHAR64(c2) == XX);
  242. if (offset == len)
  243. {
  244.     /* BAD data */
  245.     return -1;
  246. }
  247.         do
  248. {
  249.     c3 = pInBuf[offset++];
  250. }
  251. while(offset < len && c3 != '=' && CHAR64(c3) == XX);
  252. if (offset == len)
  253. {
  254.     /* BAD data */
  255.     return -1;
  256. }
  257. do
  258. {
  259.     c4 = pInBuf[offset++];
  260. }
  261. while(offset < len && c4 != '=' && CHAR64(c4) == XX);
  262. if (offset == len && c4 != '=' && CHAR64(c4) == XX)
  263. {
  264.     /* BAD data */
  265.     return -1;
  266. }
  267. if(c1 == '=' || c2 == '=')
  268. {
  269.     continue;
  270. }
  271. c1 = CHAR64(c1);
  272. c2 = CHAR64(c2);
  273. pOutBuf[outOffset++]  = ((c1 << 2) | ((c2 & 0x30) >> 4));
  274. if(c3 == '=')
  275. {
  276.     continue;
  277. }
  278. else
  279. {
  280.     c3 = CHAR64(c3);
  281.     pOutBuf[outOffset++]  = (((c2 & 0x0f) << 4) | ((c3 & 0x3c) >> 2));
  282.     if(c4 == '=')
  283.     {
  284. continue;
  285.     }
  286.     else
  287.     {
  288. c4 = CHAR64(c4);
  289. pOutBuf[outOffset++] = (((c3 & 0x03) << 6) | c4);
  290.     }
  291. }
  292.     }
  293.     return outOffset;
  294. }
  295. const char*
  296. EncodeCString(const char* pStr)
  297. {
  298.     CHXString tmp;
  299.     for(size_t i=0;i<strlen(pStr);++i)
  300.     {
  301.         switch(pStr[i])
  302.         {
  303.             case 'n':
  304.             {
  305.                 tmp += "\n";
  306.             }
  307.             break;
  308.             case 't':
  309.             {
  310.                 tmp += "\t";
  311.             }
  312.             break;
  313.             case 'r':
  314.             {
  315.                 tmp += "\r";
  316.             }
  317.             break;
  318.             case '"':
  319.             {
  320.                 tmp += "\"";
  321.             }
  322.             break;
  323.             case '\':
  324.             {
  325.                 tmp += "\\";
  326.             }
  327.             break;
  328.             default:
  329.             {
  330.                 tmp += pStr[i];
  331.             }
  332.         }
  333.     }
  334.     return tmp;
  335. }
  336. #ifdef XXXBAB
  337. void
  338. printbuf(unsigned char* pBuf, int len)
  339. {
  340.     for(int i=0; i<len; i++)
  341.     {
  342. printf("%02x ", pBuf[i]);
  343.     }
  344.     printf("n");
  345. }
  346. static unsigned char testBytes[] =
  347.     { 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 
  348.       0x4f, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10,
  349.       0x00, 0x00, 0x00, 0x00, 0x75, 0x76, 0x77, 0x78,
  350.       0x45, 0x44, 0x4a, 0x5b, 0x6c, 0x7d, 0x8e, 0x9f,
  351.       0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xb3, 0x5f, 0x78,
  352.       0x4f, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10,
  353.       0x00, 0x00, 0x00, 0x00, 0x75, 0x76, 0x77, 0x78,
  354.       0x45, 0x44, 0x4a, 0x5b, 0x6c, 0x7d, 0x8e, 0x9f,
  355.       0x45, 0x44, 0x4a, 0x5b, 0x6c, 0x7d, 0x8e, 0x9f,
  356.       0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xb3, 0x5f, 0x78,
  357.       0x4f, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10,
  358.       0x00, 0x00, 0x00, 0x00, 0x75, 0x76, 0x77, 0x78,
  359.       0x45, 0x44, 0x4a, 0x5b, 0x6c, 0x7d, 0x8e, 0x9f,
  360.       0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xb3, 0x5f, 0x78,
  361.       0x4f, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10,
  362.       0x00, 0x00, 0x00, 0x00, 0x75, 0x76, 0x77, 0x78,
  363.       0x45, 0x44, 0x4a, 0x5b, 0x6c, 0x7d, 0x8e, 0x9f,
  364.       0x77, 0x88, 0x00 };
  365. static unsigned char testBytes2[] =
  366.     { 0x7F, 0x63, 0x31, 0xBB, 0x90, 0x21, 0x32, 0x11,
  367.       0xC4 };
  368. void main()
  369. {
  370.     unsigned char encodeBuf[300]; /* Flawfinder: ignore */
  371.     unsigned char decodeBuf[300]; /* Flawfinder: ignore */
  372.     memset(encodeBuf, '', sizeof(encodeBuf));
  373.     memset(decodeBuf, '', sizeof(decodeBuf));
  374.     int rc = BinTo64(testBytes, sizeof(testBytes), encodeBuf);
  375.     printf("original size: %d, encoded size: %dn", sizeof(testBytes), rc);
  376.     printf("%sn", encodeBuf);
  377.     rc = BinFrom64(encodeBuf, rc, decodeBuf);
  378.     printf("decode size: %dn", rc);
  379.     printbuf(decodeBuf, rc);
  380. }
  381. #endif /* XXXBAB */
  382. const char escapeChars[] =
  383. {       
  384.     0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
  385.     1,1,1,1,1,1,1,1,1,1,1,1,0,0,1,1,0,1,0,0,
  386.     0,0,0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
  387.     1,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
  388.     0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
  389.     0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
  390.     0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,
  391.     0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
  392.     0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
  393.     0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
  394.     0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
  395.     0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
  396.     0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0
  397. };
  398. /*
  399.  * Function: URLEscapeBuffer
  400.  */
  401. INT32 
  402. URLEscapeBuffer(const char* pInBuf, INT32 len, char* pOutBuf)
  403. {
  404.     const char* pInputPos = pInBuf;
  405.     char* pOutputPos = pOutBuf;
  406.     char pTemp[3]; /* Flawfinder: ignore */
  407.     
  408.     if (!pInBuf || !len || !pOutBuf)
  409.     {
  410. return -1;
  411.     }
  412.     // Iterate through the input buffer
  413.     while (pInputPos < pInBuf + len)
  414.     {
  415. BOOL bIsIllegal = FALSE;
  416. if (HXIsDBCSEnabled())
  417. {
  418.     // If an illegal URL character is found, translate it
  419.     bIsIllegal = 
  420.         HXIsEqual(pInputPos, 0x7f) ||
  421.      HXIsEqual(pInputPos, '%')  ||
  422.      HXIsEqual(pInputPos, '"')  ||
  423.      HXIsEqual(pInputPos, '+')  ||
  424.      HXIsEqual(pInputPos, '<')  ||
  425. HXIsEqual(pInputPos, '>')  ||
  426.      HXIsEqual(pInputPos, ',')  ||
  427.      HXIsEqual(pInputPos, '#')  ||
  428.      HXIsEqual(pInputPos, 0x01) ||
  429.      HXIsEqual(pInputPos, 0x02) ||
  430.      HXIsEqual(pInputPos, 0x03) ||
  431.      HXIsEqual(pInputPos, 0x04) ||
  432.      HXIsEqual(pInputPos, 0x05) ||
  433.      HXIsEqual(pInputPos, 0x06) ||
  434.      HXIsEqual(pInputPos, 0x07) ||
  435.      HXIsEqual(pInputPos, 0x08) ||
  436.      HXIsEqual(pInputPos, 0x09) ||
  437.      HXIsEqual(pInputPos, 0x0a) ||
  438.      HXIsEqual(pInputPos, 0x0b) ||
  439.      HXIsEqual(pInputPos, 0x0c) ||
  440.      HXIsEqual(pInputPos, 0x0d) ||
  441.      HXIsEqual(pInputPos, 0x0e) ||
  442.      HXIsEqual(pInputPos, 0x0f) ||
  443.      HXIsEqual(pInputPos, 0x10) ||
  444.      HXIsEqual(pInputPos, 0x11) ||
  445.      HXIsEqual(pInputPos, 0x12) ||
  446.      HXIsEqual(pInputPos, 0x13) ||
  447.      HXIsEqual(pInputPos, 0x14) ||
  448.      HXIsEqual(pInputPos, 0x15) ||
  449.      HXIsEqual(pInputPos, 0x16) ||
  450.      HXIsEqual(pInputPos, 0x17) ||
  451.      HXIsEqual(pInputPos, 0x18) ||
  452.      HXIsEqual(pInputPos, 0x19) ||
  453.      HXIsEqual(pInputPos, 0x1a) ||
  454.      HXIsEqual(pInputPos, 0x1b) ||
  455.      HXIsEqual(pInputPos, 0x1c) ||
  456.      HXIsEqual(pInputPos, 0x1d) ||
  457.      HXIsEqual(pInputPos, 0x1e) ||
  458.      HXIsEqual(pInputPos, 0x1f);
  459. }
  460. else
  461. {
  462.     // Use a lookup table for improved performance
  463.     bIsIllegal = (BOOL)escapeChars[(UCHAR)*pInputPos];
  464. }
  465. if (bIsIllegal)
  466. {
  467.     SafeSprintf(pTemp, sizeof(pTemp), "%02x", *pInputPos);
  468.     *pOutputPos++ = '%';
  469.     *pOutputPos++ = pTemp[0];
  470.     *pOutputPos++ = pTemp[1];
  471. }
  472. else if (HXIsEqual(pInputPos, ' '))
  473. {
  474.     *pOutputPos++ = '+';
  475. }
  476. else
  477. {
  478.     *pOutputPos++ = *pInputPos;
  479.     if (HXIsLeadByte(*pInputPos))
  480.     {
  481.      *pOutputPos++ = *(pInputPos + 1);
  482.     }
  483. }
  484. pInputPos = HXGetNextChar(pInputPos);
  485.     }
  486.     // Return the length of the escaped content
  487.     return (pOutputPos - pOutBuf);
  488. }
  489. const char escapeCharsNoReserved[] =
  490. { //8,9,A,B,C,D,E,F
  491.     0,1,1,1,1,1,1,1, // 0x00
  492.     1,1,1,1,1,1,1,1, // 0x08
  493.     1,1,1,1,1,1,1,1, // 0x10
  494.     1,1,1,1,1,1,1,1, // 0x18
  495.     1,0,1,1,0,1,0,0, // 0x20
  496.     0,0,0,0,0,0,0,0, // 0x28
  497.     0,0,0,0,0,0,0,0, // 0x30
  498.     0,0,0,0,1,0,1,0, // 0x38
  499.     0,0,0,0,0,0,0,0, // 0x40
  500.     0,0,0,0,0,0,0,0, // 0x48
  501.     0,0,0,0,0,0,0,0, // 0x50
  502.     0,0,0,1,1,1,1,0, // 0x58
  503.     1,0,0,0,0,0,0,0, // 0x60
  504.     0,0,0,0,0,0,0,0, // 0x68
  505.     0,0,0,0,0,0,0,0, // 0x70
  506.     0,0,0,1,1,1,1,1, // 0x78
  507.     1,1,1,1,1,1,1,1, // 0x80
  508.     1,1,1,1,1,1,1,1, // 0x88
  509.     1,1,1,1,1,1,1,1, // 0x90
  510.     1,1,1,1,1,1,1,1, // 0x98
  511.     1,1,1,1,1,1,1,1, // 0xA0
  512.     1,1,1,1,1,1,1,1, // 0xA8
  513.     1,1,1,1,1,1,1,1, // 0xB0
  514.     1,1,1,1,1,1,1,1, // 0xB8
  515.     1,1,1,1,1,1,1,1, // 0xC0
  516.     1,1,1,1,1,1,1,1, // 0xC8
  517.     1,1,1,1,1,1,1,1, // 0xD0
  518.     1,1,1,1,1,1,1,1, // 0xD8
  519.     1,1,1,1,1,1,1,1, // 0xE0
  520.     1,1,1,1,1,1,1,1, // 0xE8
  521.     1,1,1,1,1,1,1,1, // 0xF0
  522.     1,1,1,1,1,1,1,1  // 0xF8
  523. };
  524. const char escapeCharsReserved[] =
  525. { //8,9,A,B,C,D,E,F     
  526.     0,1,1,1,1,1,1,1, // 0x00
  527.     1,1,1,1,1,1,1,1, // 0x08
  528.     1,1,1,1,1,1,1,1, // 0x10
  529.     1,1,1,1,1,1,1,1, // 0x18
  530.     1,0,1,1,0,1,1,0, // 0x20
  531.     0,0,0,0,0,0,0,1, // 0x28
  532.     0,0,0,0,0,0,0,0, // 0x30
  533.     0,0,1,1,1,1,1,1, // 0x38
  534.     1,0,0,0,0,0,0,0, // 0x40
  535.     0,0,0,0,0,0,0,0, // 0x48
  536.     0,0,0,0,0,0,0,0, // 0x50
  537.     0,0,0,1,1,1,1,0, // 0x58
  538.     1,0,0,0,0,0,0,0, // 0x60
  539.     0,0,0,0,0,0,0,0, // 0x68
  540.     0,0,0,0,0,0,0,0, // 0x70
  541.     0,0,0,1,1,1,1,1, // 0x78
  542.     1,1,1,1,1,1,1,1, // 0x80
  543.     1,1,1,1,1,1,1,1, // 0x88
  544.     1,1,1,1,1,1,1,1, // 0x90
  545.     1,1,1,1,1,1,1,1, // 0x98
  546.     1,1,1,1,1,1,1,1, // 0xA0
  547.     1,1,1,1,1,1,1,1, // 0xA8
  548.     1,1,1,1,1,1,1,1, // 0xB0
  549.     1,1,1,1,1,1,1,1, // 0xB8
  550.     1,1,1,1,1,1,1,1, // 0xC0
  551.     1,1,1,1,1,1,1,1, // 0xC8
  552.     1,1,1,1,1,1,1,1, // 0xD0
  553.     1,1,1,1,1,1,1,1, // 0xD8
  554.     1,1,1,1,1,1,1,1, // 0xE0
  555.     1,1,1,1,1,1,1,1, // 0xE8
  556.     1,1,1,1,1,1,1,1, // 0xF0
  557.     1,1,1,1,1,1,1,1  // 0xF8
  558. };
  559. /*
  560.  * Function: URLEscapeBufferReserved  this function will escape all potentially unsafe charactors.
  561.  */
  562. INT32 
  563. URLEscapeBuffer2(const char* pInBuf, INT32 len, char* pOutBuf, BOOL bReserved)
  564. {
  565.     const char* pInputPos = pInBuf;
  566.     char* pOutputPos = pOutBuf;
  567.     char pTemp[3];
  568.     
  569.     if (!pInBuf || !len || !pOutBuf)
  570.     {
  571. return -1;
  572.     }
  573.     const char* lookupTable = NULL;
  574.     if (bReserved)
  575.     {
  576. lookupTable = (const char*)escapeCharsReserved;
  577.     }
  578.     else
  579.     {
  580. lookupTable = (const char*)escapeCharsNoReserved;
  581.     }
  582.     
  583.  
  584.     // Iterate through the input buffer
  585.     while (pInputPos < pInBuf + len)
  586.     {
  587. // Use a lookup table for improved performance
  588. BOOL bIsIllegal = (BOOL)lookupTable[(UCHAR)*pInputPos];
  589. if (bIsIllegal)
  590. {
  591.     SafeSprintf(pTemp, sizeof(pTemp), "%02x", *pInputPos);
  592.     *pOutputPos++ = '%';
  593.     *pOutputPos++ = pTemp[0];
  594.     *pOutputPos++ = pTemp[1];
  595. }
  596. else
  597. {
  598.     *pOutputPos++ = *pInputPos;
  599. }
  600. ++pInputPos;
  601.     }
  602.     // Return the length of the escaped content
  603.     return (pOutputPos - pOutBuf);
  604. }
  605. /*
  606.  * Function: URLUnescapeBuffer
  607.  */
  608. INT32 
  609. URLUnescapeBuffer(const char* pInBuf, INT32 len, char* pOutBuf)
  610. {
  611.     char* pOutputPos = pOutBuf;
  612.     char pTemp[3];
  613.     if (!pInBuf || !len || !pOutBuf)
  614.     {
  615. return -1;
  616.     }
  617.     // Iterate through the input buffer
  618.     for (INT32 i = 0; i < len; i++)
  619.     {
  620. // Ignore whitespace
  621. if ((UCHAR)pInBuf[i] < 21)
  622. {
  623.     continue;
  624. }
  625. // If an escaped character is found, translate it
  626. else if (pInBuf[i] == '%')
  627. {
  628.     if (len < i + 3)
  629.     {
  630. // Incomplete %xx representation
  631. return -1;
  632.     }
  633.     
  634.     // Ignore whitespace
  635.     while (pInBuf[i + 1] < 21) 
  636.     { 
  637. i++;
  638. if (len < i + 3)
  639. {
  640.     return -1;
  641. }
  642.     }
  643.     pTemp[0] = pInBuf[i + 1];
  644.     // Ignore whitespace
  645.     while (pInBuf[i + 2] < 21) 
  646.     { 
  647. i++;
  648. if (len < i + 3)
  649. {
  650.     return -1;
  651. }
  652.     }
  653.     pTemp[1] = pInBuf[i + 2];
  654.     pTemp[2] = '';
  655.     *pOutputPos++ = (char)strtol(pTemp, NULL, 16);
  656.     i += 2;
  657. }
  658. else if (pInBuf[i] == '+')
  659. {
  660.     *pOutputPos++ = ' ';
  661. }
  662. else
  663. {
  664.     *pOutputPos++ = pInBuf[i];
  665. }
  666.     }
  667.     // Return the length of the escaped content
  668.     return (pOutputPos - pOutBuf);
  669. }
  670. #ifdef XXXDPS
  671. static const char* pTestTable[] =
  672. {
  673.     "this is a test, this is only a test",
  674.     "abcdefghijklmnopqrstuvwxyz0123456789/NoneOfThisShouldGetEscaped...",
  675.     "rnt,#><+"%All Of The First 10 Chars Should Get Escaped",
  676.     "Insert a DBCS test string here."
  677. };
  678. void main()
  679. {
  680.     unsigned char encodeBuf[300]; /* Flawfinder: ignore */
  681.     unsigned char decodeBuf[300]; /* Flawfinder: ignore */
  682.     for (int i = 0; i < 4; i++)
  683.     {
  684. memset(encodeBuf, '', sizeof(encodeBuf));
  685. memset(decodeBuf, '', sizeof(decodeBuf));
  686. printf("Escaping >>>%s<<<n", pTestTable[i]);
  687. int rc = URLEscapeBuffer((char*)pTestTable[i], strlen(pTestTable[i]), (char*)encodeBuf);
  688. printf("original size: %d, encoded size: %dn", strlen(pTestTable[i]), rc);
  689. printf("%sn", encodeBuf);
  690. rc = URLUnescapeBuffer((char*)encodeBuf, rc, (char*)decodeBuf);
  691. printf("decode size: %dn", rc);
  692. printf("%sn", decodeBuf);
  693. printf("n");
  694.     }
  695. }
  696. #endif /* XXXDPS */