diff options
Diffstat (limited to 'compat')
-rw-r--r-- | compat/mingw.c | 41 | ||||
-rw-r--r-- | compat/vcbuild/README | 4 |
2 files changed, 41 insertions, 4 deletions
diff --git a/compat/mingw.c b/compat/mingw.c index 6ded1c859f..858ca14a57 100644 --- a/compat/mingw.c +++ b/compat/mingw.c @@ -341,12 +341,44 @@ int mingw_mkdir(const char *path, int mode) return ret; } +static int mingw_open_append(wchar_t const *wfilename, int oflags, ...) +{ + HANDLE handle; + int fd; + DWORD create = (oflags & O_CREAT) ? OPEN_ALWAYS : OPEN_EXISTING; + + /* only these flags are supported */ + if ((oflags & ~O_CREAT) != (O_WRONLY | O_APPEND)) + return errno = ENOSYS, -1; + + /* + * FILE_SHARE_WRITE is required to permit child processes + * to append to the file. + */ + handle = CreateFileW(wfilename, FILE_APPEND_DATA, + FILE_SHARE_WRITE | FILE_SHARE_READ, + NULL, create, FILE_ATTRIBUTE_NORMAL, NULL); + if (handle == INVALID_HANDLE_VALUE) + return errno = err_win_to_posix(GetLastError()), -1; + /* + * No O_APPEND here, because the CRT uses it only to reset the + * file pointer to EOF on write(); but that is not necessary + * for a file created with FILE_APPEND_DATA. + */ + fd = _open_osfhandle((intptr_t)handle, O_BINARY); + if (fd < 0) + CloseHandle(handle); + return fd; +} + int mingw_open (const char *filename, int oflags, ...) { + typedef int (*open_fn_t)(wchar_t const *wfilename, int oflags, ...); va_list args; unsigned mode; int fd; wchar_t wfilename[MAX_PATH]; + open_fn_t open_fn; va_start(args, oflags); mode = va_arg(args, int); @@ -355,9 +387,14 @@ int mingw_open (const char *filename, int oflags, ...) if (filename && !strcmp(filename, "/dev/null")) filename = "nul"; + if (oflags & O_APPEND) + open_fn = mingw_open_append; + else + open_fn = _wopen; + if (xutftowcs_path(wfilename, filename) < 0) return -1; - fd = _wopen(wfilename, oflags, mode); + fd = open_fn(wfilename, oflags, mode); if (fd < 0 && (oflags & O_ACCMODE) != O_RDONLY && errno == EACCES) { DWORD attrs = GetFileAttributesW(wfilename); @@ -375,7 +412,7 @@ int mingw_open (const char *filename, int oflags, ...) * CREATE_ALWAYS flag of CreateFile()). */ if (fd < 0 && errno == EACCES) - fd = _wopen(wfilename, oflags & ~O_CREAT, mode); + fd = open_fn(wfilename, oflags & ~O_CREAT, mode); if (fd >= 0 && set_hidden_flag(wfilename, 1)) warning("could not mark '%s' as hidden.", filename); } diff --git a/compat/vcbuild/README b/compat/vcbuild/README index df8a6574c9..60fd873fe8 100644 --- a/compat/vcbuild/README +++ b/compat/vcbuild/README @@ -30,8 +30,8 @@ The Steps of Build Git with VS2008 the git operations. 3. Inside Git's directory run the command: - make common-cmds.h - to generate the common-cmds.h file needed to compile git. + make command-list.h + to generate the command-list.h file needed to compile git. 4. Then either build Git with the GNU Make Makefile in the Git projects root |