Commit d8563619 by Ben Straub

Split UTF-16 and UTF-8 buffer sizes for win32

Also fixed up call-sites to use the correct buffer sizes, especially
when converting to utf-8.
parent 9b7d02ff
...@@ -58,9 +58,9 @@ int git_futils_creat_locked(const char *path, const mode_t mode) ...@@ -58,9 +58,9 @@ int git_futils_creat_locked(const char *path, const mode_t mode)
int fd; int fd;
#ifdef GIT_WIN32 #ifdef GIT_WIN32
wchar_t buf[GIT_WIN_PATH]; wchar_t buf[GIT_WIN_PATH_UTF16];
git__utf8_to_16(buf, GIT_WIN_PATH, path); git__utf8_to_16(buf, GIT_WIN_PATH_UTF16, path);
fd = _wopen(buf, O_WRONLY | O_CREAT | O_TRUNC | fd = _wopen(buf, O_WRONLY | O_CREAT | O_TRUNC |
O_EXCL | O_BINARY | O_CLOEXEC, mode); O_EXCL | O_BINARY | O_CLOEXEC, mode);
#else #else
......
...@@ -486,14 +486,14 @@ bool git_path_is_empty_dir(const char *path) ...@@ -486,14 +486,14 @@ bool git_path_is_empty_dir(const char *path)
{ {
git_buf pathbuf = GIT_BUF_INIT; git_buf pathbuf = GIT_BUF_INIT;
HANDLE hFind = INVALID_HANDLE_VALUE; HANDLE hFind = INVALID_HANDLE_VALUE;
wchar_t wbuf[GIT_WIN_PATH]; wchar_t wbuf[GIT_WIN_PATH_UTF16];
WIN32_FIND_DATAW ffd; WIN32_FIND_DATAW ffd;
bool retval = true; bool retval = true;
if (!git_path_isdir(path)) return false; if (!git_path_isdir(path)) return false;
git_buf_printf(&pathbuf, "%s\\*", path); git_buf_printf(&pathbuf, "%s\\*", path);
git__utf8_to_16(wbuf, GIT_WIN_PATH, git_buf_cstr(&pathbuf)); git__utf8_to_16(wbuf, GIT_WIN_PATH_UTF16, git_buf_cstr(&pathbuf));
hFind = FindFirstFileW(wbuf, &ffd); hFind = FindFirstFileW(wbuf, &ffd);
if (INVALID_HANDLE_VALUE == hFind) { if (INVALID_HANDLE_VALUE == hFind) {
......
...@@ -893,7 +893,7 @@ static int winhttp_connect( ...@@ -893,7 +893,7 @@ static int winhttp_connect(
const char *url) const char *url)
{ {
wchar_t *ua = L"git/1.0 (libgit2 " WIDEN(LIBGIT2_VERSION) L")"; wchar_t *ua = L"git/1.0 (libgit2 " WIDEN(LIBGIT2_VERSION) L")";
wchar_t host[GIT_WIN_PATH]; wchar_t host[GIT_WIN_PATH_UTF16];
int32_t port; int32_t port;
const char *default_port = "80"; const char *default_port = "80";
int ret; int ret;
...@@ -920,7 +920,7 @@ static int winhttp_connect( ...@@ -920,7 +920,7 @@ static int winhttp_connect(
return -1; return -1;
/* Prepare host */ /* Prepare host */
git__utf8_to_16(host, GIT_WIN_PATH, t->host); git__utf8_to_16(host, GIT_WIN_PATH_UTF16, t->host);
/* Establish session */ /* Establish session */
t->session = WinHttpOpen( t->session = WinHttpOpen(
......
...@@ -25,8 +25,8 @@ static int init_filter(char *filter, size_t n, const char *dir) ...@@ -25,8 +25,8 @@ static int init_filter(char *filter, size_t n, const char *dir)
git__DIR *git__opendir(const char *dir) git__DIR *git__opendir(const char *dir)
{ {
char filter[GIT_WIN_PATH]; char filter[GIT_WIN_PATH_UTF8];
wchar_t filter_w[GIT_WIN_PATH]; wchar_t filter_w[GIT_WIN_PATH_UTF16];
git__DIR *new = NULL; git__DIR *new = NULL;
if (!dir || !init_filter(filter, sizeof(filter), dir)) if (!dir || !init_filter(filter, sizeof(filter), dir))
...@@ -40,7 +40,7 @@ git__DIR *git__opendir(const char *dir) ...@@ -40,7 +40,7 @@ git__DIR *git__opendir(const char *dir)
if (!new->dir) if (!new->dir)
goto fail; goto fail;
git__utf8_to_16(filter_w, GIT_WIN_PATH, filter); git__utf8_to_16(filter_w, GIT_WIN_PATH_UTF16, filter);
new->h = FindFirstFileW(filter_w, &new->f); new->h = FindFirstFileW(filter_w, &new->f);
if (new->h == INVALID_HANDLE_VALUE) { if (new->h == INVALID_HANDLE_VALUE) {
...@@ -101,8 +101,8 @@ struct git__dirent *git__readdir(git__DIR *d) ...@@ -101,8 +101,8 @@ struct git__dirent *git__readdir(git__DIR *d)
void git__rewinddir(git__DIR *d) void git__rewinddir(git__DIR *d)
{ {
char filter[GIT_WIN_PATH]; char filter[GIT_WIN_PATH_UTF8];
wchar_t filter_w[GIT_WIN_PATH]; wchar_t filter_w[GIT_WIN_PATH_UTF16];
if (!d) if (!d)
return; return;
...@@ -116,7 +116,7 @@ void git__rewinddir(git__DIR *d) ...@@ -116,7 +116,7 @@ void git__rewinddir(git__DIR *d)
if (!init_filter(filter, sizeof(filter), d->dir)) if (!init_filter(filter, sizeof(filter), d->dir))
return; return;
git__utf8_to_16(filter_w, GIT_WIN_PATH, filter); git__utf8_to_16(filter_w, GIT_WIN_PATH_UTF16, filter);
d->h = FindFirstFileW(filter_w, &d->f); d->h = FindFirstFileW(filter_w, &d->f);
if (d->h == INVALID_HANDLE_VALUE) if (d->h == INVALID_HANDLE_VALUE)
......
...@@ -11,7 +11,7 @@ ...@@ -11,7 +11,7 @@
struct git__dirent { struct git__dirent {
int d_ino; int d_ino;
char d_name[261]; char d_name[260*4+1];
}; };
typedef struct { typedef struct {
......
...@@ -20,9 +20,9 @@ GIT_INLINE(int) p_link(const char *old, const char *new) ...@@ -20,9 +20,9 @@ GIT_INLINE(int) p_link(const char *old, const char *new)
GIT_INLINE(int) p_mkdir(const char *path, mode_t mode) GIT_INLINE(int) p_mkdir(const char *path, mode_t mode)
{ {
wchar_t buf[GIT_WIN_PATH]; wchar_t buf[GIT_WIN_PATH_UTF16];
GIT_UNUSED(mode); GIT_UNUSED(mode);
git__utf8_to_16(buf, GIT_WIN_PATH, path); git__utf8_to_16(buf, GIT_WIN_PATH_UTF16, path);
return _wmkdir(buf); return _wmkdir(buf);
} }
......
...@@ -16,8 +16,8 @@ ...@@ -16,8 +16,8 @@
int p_unlink(const char *path) int p_unlink(const char *path)
{ {
wchar_t buf[GIT_WIN_PATH]; wchar_t buf[GIT_WIN_PATH_UTF16];
git__utf8_to_16(buf, GIT_WIN_PATH, path); git__utf8_to_16(buf, GIT_WIN_PATH_UTF16, path);
_wchmod(buf, 0666); _wchmod(buf, 0666);
return _wunlink(buf); return _wunlink(buf);
} }
...@@ -59,10 +59,10 @@ static int do_lstat( ...@@ -59,10 +59,10 @@ static int do_lstat(
const char *file_name, struct stat *buf, int posix_enotdir) const char *file_name, struct stat *buf, int posix_enotdir)
{ {
WIN32_FILE_ATTRIBUTE_DATA fdata; WIN32_FILE_ATTRIBUTE_DATA fdata;
wchar_t fbuf[GIT_WIN_PATH], lastch; wchar_t fbuf[GIT_WIN_PATH_UTF16], lastch;
int flen; int flen;
flen = git__utf8_to_16(fbuf, GIT_WIN_PATH, file_name); flen = git__utf8_to_16(fbuf, GIT_WIN_PATH_UTF16, file_name);
/* truncate trailing slashes */ /* truncate trailing slashes */
for (; flen > 0; --flen) { for (; flen > 0; --flen) {
...@@ -108,10 +108,10 @@ static int do_lstat( ...@@ -108,10 +108,10 @@ static int do_lstat(
* the length of the path pointed to, which we expect everywhere else * the length of the path pointed to, which we expect everywhere else
*/ */
if (S_ISLNK(fMode)) { if (S_ISLNK(fMode)) {
char target[GIT_WIN_PATH]; char target[GIT_WIN_PATH_UTF8];
int readlink_result; int readlink_result;
readlink_result = p_readlink(file_name, target, GIT_WIN_PATH); readlink_result = p_readlink(file_name, target, GIT_WIN_PATH_UTF8);
if (readlink_result == -1) if (readlink_result == -1)
return -1; return -1;
...@@ -165,7 +165,7 @@ int p_readlink(const char *link, char *target, size_t target_len) ...@@ -165,7 +165,7 @@ int p_readlink(const char *link, char *target, size_t target_len)
static fpath_func pGetFinalPath = NULL; static fpath_func pGetFinalPath = NULL;
HANDLE hFile; HANDLE hFile;
DWORD dwRet; DWORD dwRet;
wchar_t link_w[GIT_WIN_PATH]; wchar_t link_w[GIT_WIN_PATH_UTF16];
wchar_t* target_w; wchar_t* target_w;
int error = 0; int error = 0;
...@@ -188,7 +188,7 @@ int p_readlink(const char *link, char *target, size_t target_len) ...@@ -188,7 +188,7 @@ int p_readlink(const char *link, char *target, size_t target_len)
} }
} }
git__utf8_to_16(link_w, GIT_WIN_PATH, link); git__utf8_to_16(link_w, GIT_WIN_PATH_UTF16, link);
hFile = CreateFileW(link_w, // file to open hFile = CreateFileW(link_w, // file to open
GENERIC_READ, // open for reading GENERIC_READ, // open for reading
...@@ -254,10 +254,10 @@ int p_symlink(const char *old, const char *new) ...@@ -254,10 +254,10 @@ int p_symlink(const char *old, const char *new)
int p_open(const char *path, int flags, ...) int p_open(const char *path, int flags, ...)
{ {
wchar_t buf[GIT_WIN_PATH]; wchar_t buf[GIT_WIN_PATH_UTF16];
mode_t mode = 0; mode_t mode = 0;
git__utf8_to_16(buf, GIT_WIN_PATH, path); git__utf8_to_16(buf, GIT_WIN_PATH_UTF16, path);
if (flags & O_CREAT) { if (flags & O_CREAT) {
va_list arg_list; va_list arg_list;
...@@ -272,8 +272,8 @@ int p_open(const char *path, int flags, ...) ...@@ -272,8 +272,8 @@ int p_open(const char *path, int flags, ...)
int p_creat(const char *path, mode_t mode) int p_creat(const char *path, mode_t mode)
{ {
wchar_t buf[GIT_WIN_PATH]; wchar_t buf[GIT_WIN_PATH_UTF16];
git__utf8_to_16(buf, GIT_WIN_PATH, path); git__utf8_to_16(buf, GIT_WIN_PATH_UTF16, path);
return _wopen(buf, _O_WRONLY | _O_CREAT | _O_TRUNC | _O_BINARY, mode); return _wopen(buf, _O_WRONLY | _O_CREAT | _O_TRUNC | _O_BINARY, mode);
} }
...@@ -299,7 +299,7 @@ int p_getcwd(char *buffer_out, size_t size) ...@@ -299,7 +299,7 @@ int p_getcwd(char *buffer_out, size_t size)
int p_stat(const char* path, struct stat* buf) int p_stat(const char* path, struct stat* buf)
{ {
char target[GIT_WIN_PATH]; char target[GIT_WIN_PATH_UTF8];
int error = 0; int error = 0;
error = do_lstat(path, buf, 0); error = do_lstat(path, buf, 0);
...@@ -307,7 +307,7 @@ int p_stat(const char* path, struct stat* buf) ...@@ -307,7 +307,7 @@ int p_stat(const char* path, struct stat* buf)
/* We need not do this in a loop to unwind chains of symlinks since /* We need not do this in a loop to unwind chains of symlinks since
* p_readlink calls GetFinalPathNameByHandle which does it for us. */ * p_readlink calls GetFinalPathNameByHandle which does it for us. */
if (error >= 0 && S_ISLNK(buf->st_mode) && if (error >= 0 && S_ISLNK(buf->st_mode) &&
(error = p_readlink(path, target, GIT_WIN_PATH)) >= 0) (error = p_readlink(path, target, GIT_WIN_PATH_UTF8)) >= 0)
error = do_lstat(target, buf, 0); error = do_lstat(target, buf, 0);
return error; return error;
...@@ -315,23 +315,23 @@ int p_stat(const char* path, struct stat* buf) ...@@ -315,23 +315,23 @@ int p_stat(const char* path, struct stat* buf)
int p_chdir(const char* path) int p_chdir(const char* path)
{ {
wchar_t buf[GIT_WIN_PATH]; wchar_t buf[GIT_WIN_PATH_UTF16];
git__utf8_to_16(buf, GIT_WIN_PATH, path); git__utf8_to_16(buf, GIT_WIN_PATH_UTF16, path);
return _wchdir(buf); return _wchdir(buf);
} }
int p_chmod(const char* path, mode_t mode) int p_chmod(const char* path, mode_t mode)
{ {
wchar_t buf[GIT_WIN_PATH]; wchar_t buf[GIT_WIN_PATH_UTF16];
git__utf8_to_16(buf, GIT_WIN_PATH, path); git__utf8_to_16(buf, GIT_WIN_PATH_UTF16, path);
return _wchmod(buf, mode); return _wchmod(buf, mode);
} }
int p_rmdir(const char* path) int p_rmdir(const char* path)
{ {
int error; int error;
wchar_t buf[GIT_WIN_PATH]; wchar_t buf[GIT_WIN_PATH_UTF16];
git__utf8_to_16(buf, GIT_WIN_PATH, path); git__utf8_to_16(buf, GIT_WIN_PATH_UTF16, path);
error = _wrmdir(buf); error = _wrmdir(buf);
...@@ -347,24 +347,24 @@ int p_rmdir(const char* path) ...@@ -347,24 +347,24 @@ int p_rmdir(const char* path)
int p_hide_directory__w32(const char *path) int p_hide_directory__w32(const char *path)
{ {
wchar_t buf[GIT_WIN_PATH]; wchar_t buf[GIT_WIN_PATH_UTF16];
git__utf8_to_16(buf, GIT_WIN_PATH, path); git__utf8_to_16(buf, GIT_WIN_PATH_UTF16, path);
return (SetFileAttributesW(buf, FILE_ATTRIBUTE_HIDDEN) != 0) ? 0 : -1; return (SetFileAttributesW(buf, FILE_ATTRIBUTE_HIDDEN) != 0) ? 0 : -1;
} }
char *p_realpath(const char *orig_path, char *buffer) char *p_realpath(const char *orig_path, char *buffer)
{ {
int ret; int ret;
wchar_t orig_path_w[GIT_WIN_PATH]; wchar_t orig_path_w[GIT_WIN_PATH_UTF16];
wchar_t buffer_w[GIT_WIN_PATH]; wchar_t buffer_w[GIT_WIN_PATH_UTF16];
git__utf8_to_16(orig_path_w, GIT_WIN_PATH, orig_path); git__utf8_to_16(orig_path_w, GIT_WIN_PATH_UTF16, orig_path);
/* Implicitly use GetCurrentDirectory which can be a threading issue */ /* Implicitly use GetCurrentDirectory which can be a threading issue */
ret = GetFullPathNameW(orig_path_w, GIT_WIN_PATH, buffer_w, NULL); ret = GetFullPathNameW(orig_path_w, GIT_WIN_PATH_UTF16, buffer_w, NULL);
/* According to MSDN, a return value equals to zero means a failure. */ /* According to MSDN, a return value equals to zero means a failure. */
if (ret == 0 || ret > GIT_WIN_PATH) if (ret == 0 || ret > GIT_WIN_PATH_UTF16)
buffer = NULL; buffer = NULL;
else if (GetFileAttributesW(buffer_w) == INVALID_FILE_ATTRIBUTES) { else if (GetFileAttributesW(buffer_w) == INVALID_FILE_ATTRIBUTES) {
...@@ -448,18 +448,18 @@ int p_setenv(const char* name, const char* value, int overwrite) ...@@ -448,18 +448,18 @@ int p_setenv(const char* name, const char* value, int overwrite)
int p_access(const char* path, mode_t mode) int p_access(const char* path, mode_t mode)
{ {
wchar_t buf[GIT_WIN_PATH]; wchar_t buf[GIT_WIN_PATH_UTF16];
git__utf8_to_16(buf, GIT_WIN_PATH, path); git__utf8_to_16(buf, GIT_WIN_PATH_UTF16, path);
return _waccess(buf, mode); return _waccess(buf, mode);
} }
int p_rename(const char *from, const char *to) int p_rename(const char *from, const char *to)
{ {
wchar_t wfrom[GIT_WIN_PATH]; wchar_t wfrom[GIT_WIN_PATH_UTF16];
wchar_t wto[GIT_WIN_PATH]; wchar_t wto[GIT_WIN_PATH_UTF16];
git__utf8_to_16(wfrom, GIT_WIN_PATH, from); git__utf8_to_16(wfrom, GIT_WIN_PATH_UTF16, from);
git__utf8_to_16(wto, GIT_WIN_PATH, to); git__utf8_to_16(wto, GIT_WIN_PATH_UTF16, to);
return MoveFileExW(wfrom, wto, MOVEFILE_REPLACE_EXISTING | MOVEFILE_COPY_ALLOWED) ? 0 : -1; return MoveFileExW(wfrom, wto, MOVEFILE_REPLACE_EXISTING | MOVEFILE_COPY_ALLOWED) ? 0 : -1;
} }
......
...@@ -77,5 +77,5 @@ int git__utf8_to_16(wchar_t *dest, size_t length, const char *src) ...@@ -77,5 +77,5 @@ int git__utf8_to_16(wchar_t *dest, size_t length, const char *src)
int git__utf16_to_8(char *out, const wchar_t *input) int git__utf16_to_8(char *out, const wchar_t *input)
{ {
return WideCharToMultiByte(CP_UTF8, 0, input, -1, out, GIT_WIN_PATH, NULL, NULL); return WideCharToMultiByte(CP_UTF8, 0, input, -1, out, GIT_WIN_PATH_UTF8, NULL, NULL);
} }
...@@ -10,7 +10,8 @@ ...@@ -10,7 +10,8 @@
#ifndef INCLUDE_git_utfconv_h__ #ifndef INCLUDE_git_utfconv_h__
#define INCLUDE_git_utfconv_h__ #define INCLUDE_git_utfconv_h__
#define GIT_WIN_PATH (260 + 1) #define GIT_WIN_PATH_UTF16 (260 + 1)
#define GIT_WIN_PATH_UTF8 (260 * 4 + 1)
int git__utf8_to_16(wchar_t *dest, size_t length, const char *src); int git__utf8_to_16(wchar_t *dest, size_t length, const char *src);
int git__utf16_to_8(char *dest, const wchar_t *src); int git__utf16_to_8(char *dest, const wchar_t *src);
......
...@@ -56,17 +56,17 @@ void cl_git_rewritefile(const char *filename, const char *new_content) ...@@ -56,17 +56,17 @@ void cl_git_rewritefile(const char *filename, const char *new_content)
char *cl_getenv(const char *name) char *cl_getenv(const char *name)
{ {
wchar_t name_utf16[GIT_WIN_PATH]; wchar_t name_utf16[GIT_WIN_PATH_UTF16];
DWORD alloc_len; DWORD alloc_len;
wchar_t *value_utf16; wchar_t *value_utf16;
char *value_utf8; char *value_utf8;
git__utf8_to_16(name_utf16, GIT_WIN_PATH, name); git__utf8_to_16(name_utf16, GIT_WIN_PATH_UTF16, name);
alloc_len = GetEnvironmentVariableW(name_utf16, NULL, 0); alloc_len = GetEnvironmentVariableW(name_utf16, NULL, 0);
if (alloc_len <= 0) if (alloc_len <= 0)
return NULL; return NULL;
alloc_len = GIT_WIN_PATH; alloc_len = GIT_WIN_PATH_UTF8;
cl_assert(value_utf16 = git__calloc(alloc_len, sizeof(wchar_t))); cl_assert(value_utf16 = git__calloc(alloc_len, sizeof(wchar_t)));
GetEnvironmentVariableW(name_utf16, value_utf16, alloc_len); GetEnvironmentVariableW(name_utf16, value_utf16, alloc_len);
...@@ -81,13 +81,13 @@ char *cl_getenv(const char *name) ...@@ -81,13 +81,13 @@ char *cl_getenv(const char *name)
int cl_setenv(const char *name, const char *value) int cl_setenv(const char *name, const char *value)
{ {
wchar_t name_utf16[GIT_WIN_PATH]; wchar_t name_utf16[GIT_WIN_PATH_UTF16];
wchar_t value_utf16[GIT_WIN_PATH]; wchar_t value_utf16[GIT_WIN_PATH_UTF16];
git__utf8_to_16(name_utf16, GIT_WIN_PATH, name); git__utf8_to_16(name_utf16, GIT_WIN_PATH_UTF16, name);
if (value) { if (value) {
git__utf8_to_16(value_utf16, GIT_WIN_PATH, value); git__utf8_to_16(value_utf16, GIT_WIN_PATH_UTF16, value);
cl_assert(SetEnvironmentVariableW(name_utf16, value_utf16)); cl_assert(SetEnvironmentVariableW(name_utf16, value_utf16));
} else { } else {
/* Windows XP returns 0 (failed) when passing NULL for lpValue when /* Windows XP returns 0 (failed) when passing NULL for lpValue when
...@@ -107,12 +107,12 @@ int cl_setenv(const char *name, const char *value) ...@@ -107,12 +107,12 @@ int cl_setenv(const char *name, const char *value)
* the source is a directory, a child of the source). */ * the source is a directory, a child of the source). */
int cl_rename(const char *source, const char *dest) int cl_rename(const char *source, const char *dest)
{ {
wchar_t source_utf16[GIT_WIN_PATH]; wchar_t source_utf16[GIT_WIN_PATH_UTF16];
wchar_t dest_utf16[GIT_WIN_PATH]; wchar_t dest_utf16[GIT_WIN_PATH_UTF16];
unsigned retries = 1; unsigned retries = 1;
git__utf8_to_16(source_utf16, GIT_WIN_PATH, source); git__utf8_to_16(source_utf16, GIT_WIN_PATH_UTF16, source);
git__utf8_to_16(dest_utf16, GIT_WIN_PATH, dest); git__utf8_to_16(dest_utf16, GIT_WIN_PATH_UTF16, dest);
while (!MoveFileW(source_utf16, dest_utf16)) { while (!MoveFileW(source_utf16, dest_utf16)) {
/* Only retry if the error is ERROR_ACCESS_DENIED; /* Only retry if the error is ERROR_ACCESS_DENIED;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment