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.

140 lines
3.8 KiB

  1. /***
  2. *wsetlocal.c - Contains the setlocale function (wchar_t version)
  3. *
  4. * Copyright (c) 1993-2001, Microsoft Corporation. All rights reserved.
  5. *
  6. *Purpose:
  7. * Contains the _wsetlocale() function.
  8. *
  9. *Revision History:
  10. * 10-29-93 CFW Module created.
  11. * 01-03-94 CFW Fix for NULL locale string.
  12. * 02-07-94 CFW POSIXify.
  13. * 04-15-94 GJF Made definition off outwlocale conditional on
  14. * DLL_FOR_WIN32S.
  15. * 07-26-94 CFW Fix for bug #14663.
  16. * 01-10-95 CFW Debug CRT allocs.
  17. * 01-06-99 GJF Changes for 64-bit size_t.
  18. * 05-13-99 PML Remove Win32s
  19. * 07-31-01 PML Make thread-safer, not totally thread-safe (vs7#283330)
  20. * 02-20-02 BWT Use leave instead of returning from a try block.
  21. *
  22. *******************************************************************************/
  23. #ifndef _POSIX_
  24. #include <wchar.h>
  25. #include <stdlib.h>
  26. #include <setlocal.h>
  27. #include <locale.h>
  28. #include <dbgint.h>
  29. #include <mtdll.h>
  30. #define MAXSIZE ((MAX_LC_LEN+1) * (LC_MAX-LC_MIN+1) + CATNAMES_LEN)
  31. wchar_t * __cdecl _wsetlocale (
  32. int _category,
  33. const wchar_t *_wlocale
  34. )
  35. {
  36. size_t size;
  37. char *inlocale = NULL;
  38. char *outlocale;
  39. static wchar_t *outwlocale = NULL;
  40. wchar_t *retval;
  41. /* convert WCS string into ASCII string */
  42. if (_wlocale)
  43. {
  44. size = wcslen(_wlocale) + 1;
  45. if (NULL == (inlocale = (char *)_malloc_crt(size * sizeof(char))))
  46. return NULL;
  47. if (-1 == wcstombs(inlocale, _wlocale, size))
  48. {
  49. _free_crt (inlocale);
  50. return NULL;
  51. }
  52. }
  53. #ifdef _MT
  54. _mlock(_SETLOCALE_LOCK);
  55. __try {
  56. retval = NULL;
  57. /* set the locale and get ASCII return string */
  58. outlocale = setlocale(_category, inlocale);
  59. _free_crt (inlocale);
  60. if (NULL == outlocale)
  61. __leave;
  62. /* get space for WCS return value, first call only */
  63. if (!outwlocale)
  64. {
  65. outwlocale = (wchar_t *)_malloc_crt(MAXSIZE * sizeof(wchar_t));
  66. if (!outwlocale)
  67. __leave;
  68. }
  69. if (-1 == (size = mbstowcs(NULL, outlocale, 0)))
  70. __leave;
  71. size++;
  72. if (MAXSIZE < size)
  73. __leave;
  74. /* convert return value to WCS */
  75. if (-1 == mbstowcs(outwlocale, outlocale, size)) {
  76. _free_crt(outwlocale);
  77. outwlocale = NULL;
  78. __leave;
  79. }
  80. retval = outwlocale;
  81. } __finally {
  82. _munlock(_SETLOCALE_LOCK);
  83. }
  84. return retval;
  85. #else
  86. /* set the locale and get ASCII return string */
  87. outlocale = setlocale(_category, inlocale);
  88. _free_crt (inlocale);
  89. if (NULL == outlocale)
  90. return NULL;
  91. /* get space for WCS return value, first call only */
  92. if (!outwlocale)
  93. {
  94. outwlocale = (wchar_t *)_malloc_crt(MAXSIZE * sizeof(wchar_t));
  95. if (!outwlocale)
  96. return NULL;
  97. }
  98. if (-1 == (size = mbstowcs(NULL, outlocale, 0)))
  99. return NULL;
  100. size++;
  101. if (MAXSIZE < size)
  102. return NULL;
  103. /* convert return value to WCS */
  104. if (-1 == mbstowcs(outwlocale, outlocale, size))
  105. {
  106. _free_crt(outwlocale);
  107. outwlocale = NULL;
  108. return NULL;
  109. }
  110. return outwlocale;
  111. #endif
  112. }
  113. #endif /* _POSIX_ */