mbutils.c
上传用户:blenddy
上传日期:2007-01-07
资源大小:6495k
文件大小:6k
源码类别:

数据库系统

开发平台:

Unix_Linux

  1. /*
  2.  * This file contains public functions for conversion between
  3.  * client encoding and server internal encoding.
  4.  * (currently mule internal code (mic) is used)
  5.  * Tatsuo Ishii
  6.  * $Id: mbutils.c,v 1.6.2.1 1999/08/02 05:25:12 scrappy Exp $ */
  7. #include "postgres.h"
  8. #include "miscadmin.h"
  9. #include "mb/pg_wchar.h"
  10. static int client_encoding = -1;
  11. static void (*client_to_mic) ();/* something to MIC */
  12. static void (*client_from_mic) (); /* MIC to something */
  13. static void (*server_to_mic) ();/* something to MIC */
  14. static void (*server_from_mic) (); /* MIC to something */
  15. /*
  16.  * find encoding table entry by encoding
  17.  */
  18. static pg_encoding_conv_tbl *
  19. get_enc_ent(int encoding)
  20. {
  21. pg_encoding_conv_tbl *p = pg_conv_tbl;
  22. for (; p->encoding >= 0; p++)
  23. {
  24. if (p->encoding == encoding)
  25. return (p);
  26. }
  27. return (0);
  28. }
  29. /*
  30.  * set the client encoding. if client/server encoding is
  31.  * not supported, returns -1
  32.  */
  33. int
  34. pg_set_client_encoding(int encoding)
  35. {
  36. int current_server_encoding = GetDatabaseEncoding();
  37. client_encoding = encoding;
  38. if (client_encoding == current_server_encoding)
  39. { /* server == client? */
  40. client_to_mic = client_from_mic = 0;
  41. server_to_mic = server_from_mic = 0;
  42. }
  43. else if (current_server_encoding == MULE_INTERNAL)
  44. { /* server == MULE_INETRNAL? */
  45. client_to_mic = get_enc_ent(encoding)->to_mic;
  46. client_from_mic = get_enc_ent(encoding)->from_mic;
  47. server_to_mic = server_from_mic = 0;
  48. if (client_to_mic == 0 || client_from_mic == 0)
  49. return (-1);
  50. }
  51. else if (encoding == MULE_INTERNAL)
  52. { /* client == MULE_INETRNAL? */
  53. client_to_mic = client_from_mic = 0;
  54. server_to_mic = get_enc_ent(current_server_encoding)->to_mic;
  55. server_from_mic = get_enc_ent(current_server_encoding)->from_mic;
  56. if (server_to_mic == 0 || server_from_mic == 0)
  57. return (-1);
  58. }
  59. else
  60. {
  61. client_to_mic = get_enc_ent(encoding)->to_mic;
  62. client_from_mic = get_enc_ent(encoding)->from_mic;
  63. server_to_mic = get_enc_ent(current_server_encoding)->to_mic;
  64. server_from_mic = get_enc_ent(current_server_encoding)->from_mic;
  65. if (client_to_mic == 0 || client_from_mic == 0)
  66. return (-1);
  67. if (server_to_mic == 0 || server_from_mic == 0)
  68. return (-1);
  69. }
  70. return (0);
  71. }
  72. /*
  73.  * returns the current client encoding
  74.  */
  75. int
  76. pg_get_client_encoding()
  77. {
  78. if (client_encoding == -1)
  79. {
  80. /* this is the first time */
  81. client_encoding = GetDatabaseEncoding();
  82. }
  83. return (client_encoding);
  84. }
  85. /*
  86.  * convert client encoding to server encoding. if server_encoding ==
  87.  * client_encoding or no conversion function exists,
  88.  * returns s. So be careful.
  89.  */
  90. unsigned char *
  91. pg_client_to_server(unsigned char *s, int len)
  92. {
  93. static unsigned char b1[MAX_PARSE_BUFFER * 4]; /* is this enough? */
  94. static unsigned char b2[MAX_PARSE_BUFFER * 4]; /* is this enough? */
  95. unsigned char *p = s;
  96. if (client_encoding == GetDatabaseEncoding())
  97. return (p);
  98. if (client_to_mic)
  99. {
  100. (*client_to_mic) (s, b1, len);
  101. len = strlen(b1);
  102. p = b1;
  103. }
  104. if (server_from_mic)
  105. {
  106. (*server_from_mic) (p, b2, len);
  107. p = b2;
  108. }
  109. return (p);
  110. }
  111. /*
  112.  * convert server encoding to client encoding. if server_encoding ==
  113.  * client_encoding or no conversion function exists,
  114.  * returns s. So be careful.
  115.  */
  116. unsigned char *
  117. pg_server_to_client(unsigned char *s, int len)
  118. {
  119. static unsigned char b1[MAX_PARSE_BUFFER * 4]; /* is this enough? */
  120. static unsigned char b2[MAX_PARSE_BUFFER * 4]; /* is this enough? */
  121. unsigned char *p = s;
  122. if (client_encoding == GetDatabaseEncoding())
  123. return (p);
  124. if (server_to_mic)
  125. {
  126. (*server_to_mic) (s, b1, len);
  127. len = strlen(b1);
  128. p = b1;
  129. }
  130. if (client_from_mic)
  131. {
  132. (*client_from_mic) (p, b2, len);
  133. p = b2;
  134. }
  135. return (p);
  136. }
  137. /* convert a multi-byte string to a wchar */
  138. void
  139. pg_mb2wchar(const unsigned char *from, pg_wchar * to)
  140. {
  141. (*pg_wchar_table[GetDatabaseEncoding()].mb2wchar_with_len) (from, to, strlen(from));
  142. }
  143. /* convert a multi-byte string to a wchar with a limited length */
  144. void
  145. pg_mb2wchar_with_len(const unsigned char *from, pg_wchar * to, int len)
  146. {
  147. (*pg_wchar_table[GetDatabaseEncoding()].mb2wchar_with_len) (from, to, len);
  148. }
  149. /* returns the byte length of a multi-byte word */
  150. int
  151. pg_mblen(const unsigned char *mbstr)
  152. {
  153. return ((*pg_wchar_table[GetDatabaseEncoding()].mblen) (mbstr));
  154. }
  155. /* returns the length (counted as a wchar) of a multi-byte string */
  156. int
  157. pg_mbstrlen(const unsigned char *mbstr)
  158. {
  159. int len = 0;
  160. while (*mbstr)
  161. {
  162. mbstr += pg_mblen(mbstr);
  163. len++;
  164. }
  165. return (len);
  166. }
  167. /* returns the length (counted as a wchar) of a multi-byte string
  168.    (not necessarily  NULL terminated) */
  169. int
  170. pg_mbstrlen_with_len(const unsigned char *mbstr, int limit)
  171. {
  172. int len = 0;
  173. int l;
  174. while (*mbstr && limit > 0)
  175. {
  176. l = pg_mblen(mbstr);
  177. limit -= l;
  178. mbstr += l;
  179. len++;
  180. }
  181. return (len);
  182. }
  183. /*
  184.  * returns the length of a multi-byte string
  185.  * (not necessarily  NULL terminated)
  186.  * that is not longer than limit.
  187.  * this function does not break multi-byte word boundary.
  188.  */
  189. int
  190. pg_mbcliplen(const unsigned char *mbstr, int len, int limit)
  191. {
  192. int clen = 0;
  193. int l;
  194. while (*mbstr && len > 0)
  195. {
  196. l = pg_mblen(mbstr);
  197. if ((clen + l) > limit)
  198. break;
  199. clen += l;
  200. if (clen == limit)
  201. break;
  202. len -= l;
  203. mbstr += l;
  204. }
  205. return (clen);
  206. }
  207. /*
  208.  * fuctions for utils/init
  209.  */
  210. static int DatabaseEncoding = MULTIBYTE;
  211. void
  212. SetDatabaseEncoding(int encoding)
  213. {
  214. DatabaseEncoding = encoding;
  215. }
  216. int
  217. GetDatabaseEncoding()
  218. {
  219. return (DatabaseEncoding);
  220. }
  221. /* for builtin-function */
  222. const char *
  223. getdatabaseencoding()
  224. {
  225. return (pg_encoding_to_char(DatabaseEncoding));
  226. }
  227. /* set and get template1 database encoding */
  228. static int templateEncoding;
  229. void
  230. SetTemplateEncoding(int encoding)
  231. {
  232. templateEncoding = encoding;
  233. }
  234. int
  235. GetTemplateEncoding()
  236. {
  237. return (templateEncoding);
  238. }