Browse Source

url_encode/decode

David Rose 14 years ago
parent
commit
a40d6cfc36
2 changed files with 109 additions and 0 deletions
  1. 103 0
      direct/src/plugin/wstring_encode.cxx
  2. 6 0
      direct/src/plugin/wstring_encode.h

+ 103 - 0
direct/src/plugin/wstring_encode.cxx

@@ -14,6 +14,10 @@
 
 #include "wstring_encode.h"
 
+#include <ctype.h>
+#include <sstream>
+#include <iomanip>
+
 #ifdef _WIN32
 #include <windows.h>
 #endif  // _WIN32
@@ -70,3 +74,102 @@ string_to_wstring(wstring &result, const string &source) {
   return success;
 }
 #endif  // _WIN32
+
+////////////////////////////////////////////////////////////////////
+//     Function: parse_hexdigit
+//  Description: Parses a single hex digit.  Returns true on success,
+//               false on failure.  On success, fills result with the
+//               parsed value, an integer in the range 0..15.
+////////////////////////////////////////////////////////////////////
+bool
+parse_hexdigit(int &result, char digit) {
+  if (isdigit(digit)) {
+    result = digit - '0';
+    return true;
+  } else if (isxdigit(digit)) {
+    result = tolower(digit) - 'a' + 10;
+    return true;
+  }
+  return false;
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: url_quote
+//  Description: Applies URL quoting to source and stores the result
+//               in result.
+////////////////////////////////////////////////////////////////////
+void
+url_quote(string &result, const string &source) {
+  ostringstream strm;
+  strm << hex << setfill('0');
+  for (size_t p = 0; p < source.length(); ++p) {
+    if (source[p] < 0x20 || source[p] >= 0x7f) {
+      strm << "%" << setw(2) << (unsigned int)source[p];
+    } else {
+      switch (source[p]) {
+      case ' ':
+      case '<':
+      case '>':
+      case '#':
+      case '%':
+      case '{':
+      case '}':
+      case '|':
+      case '\\':
+      case '^':
+      case '~':
+      case '[':
+      case ']':
+      case '`':
+      case ';':
+      case '?':
+      case ':':
+      case '@':
+      case '=':
+      case '&':
+      case '$':
+        strm << "%" << setw(2) << (unsigned int)source[p];
+        break;
+
+      default:
+        strm << (char)source[p];
+      }
+    }
+  }
+  result = strm.str();
+}
+
+////////////////////////////////////////////////////////////////////
+//     Function: url_unquote
+//  Description: Removes URL quoting from source and stores the result
+//               in result.
+////////////////////////////////////////////////////////////////////
+void
+url_unquote(string &result, const string &source) {
+  result = string();
+  size_t p = 0;
+  while (p < source.length()) {
+    if (source[p] == '%') {
+      ++p;
+      int ch = 0;
+      if (p < source.length()) {
+        int digit;
+        if (parse_hexdigit(digit, source[p])) {
+          ch += (digit << 4);
+        }
+        ++p;
+      }
+      if (p < source.length()) {
+        int digit;
+        if (parse_hexdigit(digit, source[p])) {
+          ch += digit;
+        }
+        ++p;
+      }
+      result += (char)ch;
+    } else {
+      result += source[p];
+      ++p;
+    }
+  }
+}

+ 6 - 0
direct/src/plugin/wstring_encode.h

@@ -37,6 +37,12 @@ inline ostream &operator << (ostream &out, const wstring &str) {
 
 #endif // _WIN32
 
+// Some handy functions for applying and removing URL escape codes,
+// which are used to pass parameters safely to p3dCert on the command
+// line.
+void url_quote(string &result, const string &source);
+void url_unquote(string &result, const string &source);
+
 #endif