diff options
author | Corinna Vinschen <corinna@vinschen.de> | 2011-12-22 12:25:10 +0000 |
---|---|---|
committer | Corinna Vinschen <corinna@vinschen.de> | 2011-12-22 12:25:10 +0000 |
commit | 3a24189bbae9d1b1943e17038e78bb7d65f2a848 (patch) | |
tree | 6a8935c6f5899db38525d5b9daeae79cf1c0e707 /winsup/cygwin/fhandler_process.cc | |
parent | 3a03267d6d695b678128db6a8b7028b8b5f93e1f (diff) | |
download | cygnal-3a24189bbae9d1b1943e17038e78bb7d65f2a848.tar.gz cygnal-3a24189bbae9d1b1943e17038e78bb7d65f2a848.tar.bz2 cygnal-3a24189bbae9d1b1943e17038e78bb7d65f2a848.zip |
* external.cc (cygwin_internal): Implement CW_ALLOC_DRIVE_MAP,
CW_MAP_DRIVE_MAP, CW_FREE_DRIVE_MAP.
* fhandler_process.cc: Include mount.h.
(get_volume_path_names_for_volume_name): Move to mount.cc.
(struct dos_drive_mappings): Ditto.
* mount.cc (get_volume_path_names_for_volume_name): Move here.
(dos_drive_mappings::dos_drive_mappings): Ditto.
(dos_drive_mappings::fixup_if_match): Ditto.
(dos_drive_mappings::~dos_drive_mappings): Ditto.
* mount.h (class dos_drive_mappings): Declare her.
* include/sys/cygwin.h (cygwin_getinfo_types): Add CW_ALLOC_DRIVE_MAP,
CW_MAP_DRIVE_MAP, CW_FREE_DRIVE_MAP.
* include/cygwin/version.h: Bump API minor number.
Diffstat (limited to 'winsup/cygwin/fhandler_process.cc')
-rw-r--r-- | winsup/cygwin/fhandler_process.cc | 164 |
1 files changed, 1 insertions, 163 deletions
diff --git a/winsup/cygwin/fhandler_process.cc b/winsup/cygwin/fhandler_process.cc index 18d1ea90f..12ba292c7 100644 --- a/winsup/cygwin/fhandler_process.cc +++ b/winsup/cygwin/fhandler_process.cc @@ -25,6 +25,7 @@ details. */ #include "ntdll.h" #include "cygtls.h" #include "pwdgrp.h" +#include "mount.h" #include "tls_pbuf.h" #include <sys/param.h> #include <ctype.h> @@ -541,169 +542,6 @@ format_process_winexename (void *data, char *&destbuf) return len + 1; } -static bool -get_volume_path_names_for_volume_name (LPCWSTR vol, LPWSTR mounts) -{ - DWORD len; - if (GetVolumePathNamesForVolumeNameW (vol, mounts, NT_MAX_PATH, &len)) - return true; - - /* Windows 2000 doesn't have GetVolumePathNamesForVolumeNameW. - Just assume that mount points are not longer than MAX_PATH. */ - WCHAR drives[MAX_PATH], dvol[MAX_PATH], mp[MAX_PATH + 3]; - if (!GetLogicalDriveStringsW (MAX_PATH, drives)) - return false; - for (PWCHAR drive = drives; *drive; drive = wcschr (drive, '\0') + 1) - { - if (!GetVolumeNameForVolumeMountPointW (drive, dvol, MAX_PATH)) - continue; - if (!wcscasecmp (vol, dvol)) - mounts = wcpcpy (mounts, drive) + 1; - wcscpy (mp, drive); - HANDLE h = FindFirstVolumeMountPointW (dvol, mp + 3, MAX_PATH); - if (h == INVALID_HANDLE_VALUE) - continue; - do - { - if (GetVolumeNameForVolumeMountPointW (mp, dvol, MAX_PATH)) - if (!wcscasecmp (vol, dvol)) - mounts = wcpcpy (mounts, drive) + 1; - } - while (FindNextVolumeMountPointW (h, mp, MAX_PATH)); - FindVolumeMountPointClose (h); - } - *mounts = L'\0'; - return true; -} - -struct dos_drive_mappings -{ - struct mapping - { - mapping *next; - size_t doslen; - size_t ntlen; - wchar_t *dospath; - wchar_t *ntdevpath; - }; - mapping *mappings; - - dos_drive_mappings () - : mappings(0) - { - tmp_pathbuf tp; - wchar_t vol[64]; /* Long enough for Volume GUID string */ - wchar_t *devpath = tp.w_get (); - wchar_t *mounts = tp.w_get (); - - /* Iterate over all volumes, fetch the first path from the list of - DOS paths the volume is mounted to, or use the GUID volume path - otherwise. */ - HANDLE sh = FindFirstVolumeW (vol, 64); - if (sh == INVALID_HANDLE_VALUE) - debug_printf ("FindFirstVolumeW, %E"); - else - do - { - /* Skip drives which are not mounted. */ - if (!get_volume_path_names_for_volume_name (vol, mounts) - || mounts[0] == L'\0') - continue; - *wcsrchr (vol, L'\\') = L'\0'; - if (QueryDosDeviceW (vol + 4, devpath, NT_MAX_PATH)) - { - /* The DOS drive mapping can be another symbolic link. If so, - the mapping won't work since the section name is the name - after resolving all symlinks. Resolve symlinks here, too. */ - for (int syml_cnt = 0; syml_cnt < SYMLOOP_MAX; ++syml_cnt) - { - UNICODE_STRING upath; - OBJECT_ATTRIBUTES attr; - NTSTATUS status; - HANDLE h; - - RtlInitUnicodeString (&upath, devpath); - InitializeObjectAttributes (&attr, &upath, - OBJ_CASE_INSENSITIVE, NULL, NULL); - status = NtOpenSymbolicLinkObject (&h, SYMBOLIC_LINK_QUERY, - &attr); - if (!NT_SUCCESS (status)) - break; - RtlInitEmptyUnicodeString (&upath, devpath, (NT_MAX_PATH - 1) - * sizeof (WCHAR)); - status = NtQuerySymbolicLinkObject (h, &upath, NULL); - NtClose (h); - if (!NT_SUCCESS (status)) - break; - devpath[upath.Length / sizeof (WCHAR)] = L'\0'; - } - mapping *m = new mapping (); - if (m) - { - m->dospath = wcsdup (mounts); - m->ntdevpath = wcsdup (devpath); - if (!m->dospath || !m->ntdevpath) - { - free (m->dospath); - free (m->ntdevpath); - delete m; - continue; - } - m->doslen = wcslen (m->dospath); - m->dospath[--m->doslen] = L'\0'; /* Drop trailing backslash */ - m->ntlen = wcslen (m->ntdevpath); - m->next = mappings; - mappings = m; - } - } - else - debug_printf ("Unable to determine the native mapping for %ls " - "(error %lu)", vol, GetLastError ()); - } - while (FindNextVolumeW (sh, vol, 64)); - FindVolumeClose (sh); - } - - wchar_t *fixup_if_match (wchar_t *path) - { - /* Check for network drive first. */ - if (!wcsncmp (path, L"\\Device\\Mup\\", 12)) - { - path += 10; - path[0] = L'\\'; - return path; - } - /* Then test local drives. */ - for (mapping *m = mappings; m; m = m->next) - if (!wcsncmp (m->ntdevpath, path, m->ntlen)) - { - wchar_t *tmppath; - - if (m->ntlen > m->doslen) - wcsncpy (path += m->ntlen - m->doslen, m->dospath, m->doslen); - else if ((tmppath = wcsdup (path + m->ntlen)) != NULL) - { - wcpcpy (wcpcpy (path, m->dospath), tmppath); - free (tmppath); - } - break; - } - return path; - } - - ~dos_drive_mappings () - { - mapping *n = 0; - for (mapping *m = mappings; m; m = n) - { - n = m->next; - free (m->dospath); - free (m->ntdevpath); - delete m; - } - } -}; - struct heap_info { struct heap |