зеркало из https://github.com/microsoft/git.git
Win32: implement basic symlink() functionality (file symlinks only)
Implement symlink() that always creates file symlinks. Fails with ENOSYS if symlinks are disabled or unsupported. Note: CreateSymbolicLinkW() was introduced with symlink support in Windows Vista. For compatibility with Windows XP, we need to load it dynamically and fail gracefully if it isnt's available. Signed-off-by: Karsten Blees <blees@dcon.de>
This commit is contained in:
Родитель
d92a1f86e8
Коммит
9714d3fb8d
|
@ -2730,6 +2730,34 @@ int link(const char *oldpath, const char *newpath)
|
|||
return 0;
|
||||
}
|
||||
|
||||
int symlink(const char *target, const char *link)
|
||||
{
|
||||
wchar_t wtarget[MAX_LONG_PATH], wlink[MAX_LONG_PATH];
|
||||
int len;
|
||||
|
||||
/* fail if symlinks are disabled or API is not supported (WinXP) */
|
||||
if (!has_symlinks) {
|
||||
errno = ENOSYS;
|
||||
return -1;
|
||||
}
|
||||
|
||||
if ((len = xutftowcs_long_path(wtarget, target)) < 0
|
||||
|| xutftowcs_long_path(wlink, link) < 0)
|
||||
return -1;
|
||||
|
||||
/* convert target dir separators to backslashes */
|
||||
while (len--)
|
||||
if (wtarget[len] == '/')
|
||||
wtarget[len] = '\\';
|
||||
|
||||
/* create file symlink */
|
||||
if (!CreateSymbolicLinkW(wlink, wtarget, 0)) {
|
||||
errno = err_win_to_posix(GetLastError());
|
||||
return -1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
#ifndef _WINNT_H
|
||||
/*
|
||||
* The REPARSE_DATA_BUFFER structure is defined in the Windows DDK (in
|
||||
|
|
|
@ -125,8 +125,6 @@ struct utsname {
|
|||
* trivial stubs
|
||||
*/
|
||||
|
||||
static inline int symlink(const char *oldpath, const char *newpath)
|
||||
{ errno = ENOSYS; return -1; }
|
||||
static inline int fchmod(int fildes, mode_t mode)
|
||||
{ errno = ENOSYS; return -1; }
|
||||
#ifndef __MINGW64_VERSION_MAJOR
|
||||
|
@ -217,6 +215,7 @@ int setitimer(int type, struct itimerval *in, struct itimerval *out);
|
|||
int sigaction(int sig, struct sigaction *in, struct sigaction *out);
|
||||
int link(const char *oldpath, const char *newpath);
|
||||
int uname(struct utsname *buf);
|
||||
int symlink(const char *target, const char *link);
|
||||
int readlink(const char *path, char *buf, size_t bufsiz);
|
||||
|
||||
/*
|
||||
|
|
Загрузка…
Ссылка в новой задаче