merge revision(s) 58745,58780,59040,60743: [Backport #13863]

rb_w32_ugetcwd: UTF-8 version getcwd

	* dir.c (rb_dir_getwd): convert from UTF-8.

	* win32/win32.c (w32_getcwd): codepage aware getcwd using
	  GetCurrentDirectoryW.
	potential memory leak

	* dir.c (rb_dir_getwd): get rid of potential memory leak.

	* util.c (ruby_getcwd): ditto.
	file.c: realpath in OS path encoding

	* dir.c (rb_dir_getwd_ospath): return cwd path in the OS path
	  encoding.

	* file.c (rb_realpath_internal): work in the OS path encoding
	load.c: cwd encoding

	* load.c (rb_get_expanded_load_path): save cwd cache in OS path
	  encoding, to get rid of unnecessary conversion and infinite
	  loading when it needs encoding conversion.
	  [ruby-dev:50221] [Bug #13863]

git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/branches/ruby_2_4@62784 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
This commit is contained in:
nagachika 2018-03-16 17:34:44 +00:00
parent 3ca42c0435
commit 2368dbdfa3
9 changed files with 118 additions and 44 deletions

View file

@ -4654,43 +4654,61 @@ clock_getres(clockid_t clock_id, struct timespec *sp)
}
/* License: Ruby's */
char *
rb_w32_getcwd(char *buffer, int size)
static char *
w32_getcwd(char *buffer, int size, UINT cp)
{
char *p = buffer;
int len;
WCHAR *p;
int wlen, len;
len = GetCurrentDirectory(0, NULL);
len = GetCurrentDirectoryW(0, NULL);
if (!len) {
errno = map_errno(GetLastError());
return NULL;
}
if (p) {
if (buffer && size < len) {
errno = ERANGE;
return NULL;
}
p = ALLOCA_N(WCHAR, len);
if (!GetCurrentDirectoryW(len, p)) {
errno = map_errno(GetLastError());
return NULL;
}
wlen = translate_wchar(p, L'\\', L'/') - p + 1;
len = WideCharToMultiByte(cp, 0, p, wlen, NULL, 0, NULL, NULL);
if (buffer) {
if (size < len) {
errno = ERANGE;
return NULL;
}
}
else {
p = malloc(len);
size = len;
if (!p) {
buffer = malloc(len);
if (!buffer) {
errno = ENOMEM;
return NULL;
}
}
WideCharToMultiByte(cp, 0, p, wlen, buffer, len, NULL, NULL);
if (!GetCurrentDirectory(size, p)) {
errno = map_errno(GetLastError());
if (!buffer)
free(p);
return NULL;
}
return buffer;
}
translate_char(p, '\\', '/', filecp());
/* License: Ruby's */
char *
rb_w32_getcwd(char *buffer, int size)
{
return w32_getcwd(buffer, size, filecp());
}
return p;
/* License: Ruby's */
char *
rb_w32_ugetcwd(char *buffer, int size)
{
return w32_getcwd(buffer, size, CP_UTF8);
}
/* License: Artistic or GPL */