AutoUrl.h 2.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141
  1. #ifndef NULLSOFT_AUTOURLH
  2. #define NULLSOFT_AUTOURLH
  3. #include <windows.h>
  4. #include "AutoChar.h"
  5. /* benski> i'm sure there's a nice optimized way of doing this, but I need to implement it _right now_ */
  6. #define HEXCASE(d) case 0x##d: return #@d
  7. inline char quickhex(unsigned char in)
  8. {
  9. switch (in)
  10. {
  11. HEXCASE(0);
  12. HEXCASE(1);
  13. HEXCASE(2);
  14. HEXCASE(3);
  15. HEXCASE(4);
  16. HEXCASE(5);
  17. HEXCASE(6);
  18. HEXCASE(7);
  19. HEXCASE(8);
  20. HEXCASE(9);
  21. HEXCASE(A);
  22. HEXCASE(B);
  23. HEXCASE(C);
  24. HEXCASE(D);
  25. HEXCASE(E);
  26. HEXCASE(F);
  27. }
  28. return 0;
  29. }
  30. /* encodes a UTF-8 string into a buffer */
  31. inline void AutoUrl_Encode(const char *in, char *out, size_t len)
  32. {
  33. if (!len)
  34. return;
  35. char *dest=out;
  36. const unsigned char *src = (const unsigned char *)in;
  37. while (*src && --len)
  38. {
  39. if ((*src >= 'A' && *src <= 'Z') ||
  40. (*src >= 'a' && *src <= 'z') ||
  41. (*src >= '0' && *src <= '9') || *src == '.' || *src == '_' || *src == '-' || *src == '~')
  42. {
  43. *dest++=*src++;
  44. }
  45. else if (len > 2)
  46. {
  47. int i = *src++;
  48. *dest++ = '%';
  49. int b = (i >> 4) & 15;
  50. if (b < 10) *dest++ = (char)('0' + b);
  51. else *dest++ = (char)('A' + b - 10);
  52. b = i & 15;
  53. if (b < 10) *dest++ = (char)('0' + b);
  54. else *dest++ = (char)('A' + b - 10);
  55. }
  56. else
  57. break;
  58. }
  59. *dest=0;
  60. }
  61. inline char *AutoUrlDupN(const wchar_t *convert, size_t len)
  62. {
  63. if (!convert)
  64. return 0;
  65. AutoCharN utf8(convert, len, CP_UTF8);
  66. size_t size = strlen(utf8)*3+1; // one byte might get encoded to 3 bytes, so we'll malloc for worst-case
  67. char *url= (char *)malloc(size*sizeof(char));
  68. AutoUrl_Encode(utf8, url, size);
  69. return url;
  70. }
  71. inline char *AutoUrlDup(const wchar_t *convert)
  72. {
  73. if (!convert)
  74. return 0;
  75. AutoChar utf8(convert, CP_UTF8);
  76. size_t size = strlen(utf8)*3+1; // one byte might get encoded to 3 bytes, so we'll malloc for worst-case
  77. char *url= (char *)malloc(size*sizeof(char));
  78. AutoUrl_Encode(utf8, url, size);
  79. return url;
  80. }
  81. inline char *AutoUrlDup(const char *utf8)
  82. {
  83. if (!utf8)
  84. return 0;
  85. size_t size = strlen(utf8)*3+1; // one byte might get encoded to 3 bytes, so we'll malloc for worst-case
  86. char *url= (char *)malloc(size*sizeof(char));
  87. AutoUrl_Encode(utf8, url, size);
  88. return url;
  89. }
  90. class AutoUrl
  91. {
  92. public:
  93. AutoUrl(const wchar_t *convert) : narrow(0)
  94. {
  95. narrow = AutoUrlDup(convert);
  96. }
  97. AutoUrl(const wchar_t *convert, size_t len) : narrow(0)
  98. {
  99. narrow = AutoUrlDupN(convert, len);
  100. }
  101. AutoUrl(const char *convert) : narrow(0)
  102. {
  103. narrow = AutoUrlDup(convert);
  104. }
  105. AutoUrl(const AutoUrl &convert) : narrow(0)
  106. {
  107. if (convert.narrow)
  108. narrow = _strdup(convert.narrow);
  109. }
  110. ~AutoUrl()
  111. {
  112. free(narrow);
  113. narrow=0;
  114. }
  115. operator const char *()
  116. {
  117. return narrow;
  118. }
  119. operator char *()
  120. {
  121. return narrow;
  122. }
  123. private:
  124. char *narrow;
  125. };
  126. #endif