Welcome to mirror list, hosted at ThFree Co, Russian Federation.

cygwin.com/git/newlib-cygwin.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/winsup
diff options
context:
space:
mode:
authorCorinna Vinschen <corinna@vinschen.de>2007-01-16 21:01:06 +0300
committerCorinna Vinschen <corinna@vinschen.de>2007-01-16 21:01:06 +0300
commitcbe2437b281270f1647ba63fb16aa4d6ed07298d (patch)
tree327f0a88867d6cb1affbb1e8fbf0abc673ca8a73 /winsup
parentc4c8d06b1abd8ea46788e4990690c696bf6edf7f (diff)
* autoload.cc (RtlAnsiStringToUnicodeString): Define.
(RtlOemStringToUnicodeString): Define. * ntdll.h (struct _RTL_USER_PROCESS_PARAMETERS): Define. (struct _PEB): Redefine with a bit of content. (RtlAnsiStringToUnicodeString): Declare. (RtlOemStringToUnicodeString): Declare. * path.cc: Include ntdll.h. (_upp): New global variable pointing to user process parameter block. (get_user_proc_parms): New static function to retrieve user process parameter block. (close_user_proc_parms_cwd_handle): New function to close handle to current working directory in user process parameter block. (cwdstuff::init): Drop redundant declaration of dynamically_loaded. Set current dir only on 9x. Call close_user_proc_parms_cwd_handle on NT instead. (cwdstuff::keep_in_sync): Only on 9x. (cwdstuff::set): Keep behaviour on 9x. On NT write cwd path into user process parameter block and set cwd handle to NULL. Fix comments to reflect new behaviour.
Diffstat (limited to 'winsup')
-rw-r--r--winsup/cygwin/ChangeLog22
-rw-r--r--winsup/cygwin/autoload.cc2
-rw-r--r--winsup/cygwin/ntdll.h47
-rw-r--r--winsup/cygwin/path.cc89
4 files changed, 144 insertions, 16 deletions
diff --git a/winsup/cygwin/ChangeLog b/winsup/cygwin/ChangeLog
index 6163e9120..786ba4cb0 100644
--- a/winsup/cygwin/ChangeLog
+++ b/winsup/cygwin/ChangeLog
@@ -1,5 +1,27 @@
2007-01-16 Corinna Vinschen <corinna@vinschen.de>
+ * autoload.cc (RtlAnsiStringToUnicodeString): Define.
+ (RtlOemStringToUnicodeString): Define.
+ * ntdll.h (struct _RTL_USER_PROCESS_PARAMETERS): Define.
+ (struct _PEB): Redefine with a bit of content.
+ (RtlAnsiStringToUnicodeString): Declare.
+ (RtlOemStringToUnicodeString): Declare.
+ * path.cc: Include ntdll.h.
+ (_upp): New global variable pointing to user process parameter block.
+ (get_user_proc_parms): New static function to retrieve user process
+ parameter block.
+ (close_user_proc_parms_cwd_handle): New function to close handle to
+ current working directory in user process parameter block.
+ (cwdstuff::init): Drop redundant declaration of dynamically_loaded.
+ Set current dir only on 9x. Call close_user_proc_parms_cwd_handle
+ on NT instead.
+ (cwdstuff::keep_in_sync): Only on 9x.
+ (cwdstuff::set): Keep behaviour on 9x. On NT write cwd path into user
+ process parameter block and set cwd handle to NULL. Fix comments to
+ reflect new behaviour.
+
+2007-01-16 Corinna Vinschen <corinna@vinschen.de>
+
* fhandler_socket.cc (fhandler_socket::ioctl): Handle SIOCGIFINDEX.
* net.cc (get_2k_ifconf): Ditto.
(get_nt_ifconf): Fake SIOCGIFINDEX.
diff --git a/winsup/cygwin/autoload.cc b/winsup/cygwin/autoload.cc
index 62e2a3b63..4a8d1d1d9 100644
--- a/winsup/cygwin/autoload.cc
+++ b/winsup/cygwin/autoload.cc
@@ -409,9 +409,11 @@ LoadDLLfuncNt (NtSetInformationFile, 20, ntdll)
LoadDLLfuncNt (NtSetSecurityObject, 12, ntdll)
LoadDLLfuncNt (NtUnlockVirtualMemory, 16, ntdll)
LoadDLLfuncNt (NtUnmapViewOfSection, 8, ntdll)
+LoadDLLfuncNt (RtlAnsiStringToUnicodeString, 12, ntdll)
LoadDLLfuncNt (RtlInitUnicodeString, 8, ntdll)
LoadDLLfuncNt (RtlIsDosDeviceName_U, 4, ntdll)
LoadDLLfuncNt (RtlNtStatusToDosError, 4, ntdll)
+LoadDLLfuncNt (RtlOemStringToUnicodeString, 12, ntdll)
LoadDLLfuncEx (EnumProcessModules, 16, psapi, 1)
LoadDLLfuncEx (GetModuleFileNameExA, 16, psapi, 1)
diff --git a/winsup/cygwin/ntdll.h b/winsup/cygwin/ntdll.h
index 53c21320b..fc56ce00c 100644
--- a/winsup/cygwin/ntdll.h
+++ b/winsup/cygwin/ntdll.h
@@ -428,7 +428,48 @@ typedef struct _KERNEL_USER_TIMES
LARGE_INTEGER UserTime;
} KERNEL_USER_TIMES, *PKERNEL_USER_TIMES;
-typedef void *PPEB;
+typedef struct _RTL_USER_PROCESS_PARAMETERS
+{
+ ULONG AllocationSize;
+ ULONG Size;
+ ULONG Flags;
+ ULONG DebugFlags;
+ HANDLE hConsole;
+ ULONG ProcessGroup;
+ HANDLE hStdInput;
+ HANDLE hStdOutput;
+ HANDLE hStdError;
+ UNICODE_STRING CurrentDirectoryName;
+ HANDLE CurrentDirectoryHandle;
+ UNICODE_STRING DllPath;
+ UNICODE_STRING ImagePathName;
+ UNICODE_STRING CommandLine;
+ PWSTR Environment;
+ ULONG dwX;
+ ULONG dwY;
+ ULONG dwXSize;
+ ULONG dwYSize;
+ ULONG dwXCountChars;
+ ULONG dwYCountChars;
+ ULONG dwFillAttribute;
+ ULONG dwFlags;
+ ULONG wShowWindow;
+ UNICODE_STRING WindowTitle;
+ UNICODE_STRING DesktopInfo;
+ UNICODE_STRING ShellInfo;
+ UNICODE_STRING RuntimeInfo;
+} RTL_USER_PROCESS_PARAMETERS, *PRTL_USER_PROCESS_PARAMETERS;
+
+typedef struct _PEB
+{
+ BYTE Reserved1[2];
+ BYTE BeingDebugged;
+ BYTE Reserved2[9];
+ PVOID LoaderData;
+ PRTL_USER_PROCESS_PARAMETERS ProcessParameters;
+ BYTE Reserved3[448];
+ ULONG SessionId;
+} PEB, *PPEB;
typedef struct _PROCESS_BASIC_INFORMATION
{
@@ -669,7 +710,11 @@ extern "C"
PSECURITY_DESCRIPTOR);
NTSTATUS NTAPI NtUnlockVirtualMemory (HANDLE, PVOID *, ULONG *, ULONG);
NTSTATUS NTAPI NtUnmapViewOfSection (HANDLE, PVOID);
+ NTSTATUS NTAPI RtlAnsiStringToUnicodeString (PUNICODE_STRING, PANSI_STRING,
+ BOOLEAN);
VOID NTAPI RtlInitUnicodeString (PUNICODE_STRING, PCWSTR);
ULONG NTAPI RtlIsDosDeviceName_U (PCWSTR);
ULONG NTAPI RtlNtStatusToDosError (NTSTATUS);
+ NTSTATUS NTAPI RtlOemStringToUnicodeString (PUNICODE_STRING, POEM_STRING,
+ BOOLEAN);
}
diff --git a/winsup/cygwin/path.cc b/winsup/cygwin/path.cc
index bbc023968..287c6f69b 100644
--- a/winsup/cygwin/path.cc
+++ b/winsup/cygwin/path.cc
@@ -77,6 +77,7 @@ details. */
#include "cygtls.h"
#include "environ.h"
#include <assert.h>
+#include <ntdll.h>
bool dos_file_warning = true;
static int normalize_win32_path (const char *, char *, char *&);
@@ -4153,18 +4154,50 @@ cwdstuff::get_hash ()
extern char windows_system_directory[];
+static PRTL_USER_PROCESS_PARAMETERS _upp NO_COPY;
+
+static PRTL_USER_PROCESS_PARAMETERS
+get_user_proc_parms ()
+{
+ if (!_upp)
+ {
+ NTSTATUS stat;
+ PROCESS_BASIC_INFORMATION pbi;
+ stat = NtQueryInformationProcess (GetCurrentProcess (),
+ ProcessBasicInformation,
+ &pbi, sizeof pbi, NULL);
+ if (!NT_SUCCESS (stat))
+ api_fatal ("Can't retrieve process parameters, status %p", stat);
+ _upp = pbi.PebBaseAddress->ProcessParameters;
+ }
+ return _upp;
+}
+
+static void
+close_user_proc_parms_cwd_handle ()
+{
+ PHANDLE phdl = &get_user_proc_parms ()->CurrentDirectoryHandle;
+ if (*phdl)
+ {
+ NtClose (*phdl);
+ *phdl = NULL;
+ }
+}
+
/* Initialize cygcwd 'muto' for serializing access to cwd info. */
void
cwdstuff::init ()
{
- extern int dynamically_loaded;
cwd_lock.init ("cwd_lock");
get_initial ();
if (!dynamically_loaded && !keep_in_sync ())
{
- /* Actually chdir into the system dir to avoid cwd problems. See comment
- in cwdstuff::set below. */
- SetCurrentDirectory (windows_system_directory);
+ /* Actually chdir into the system dir to avoid cwd problems on 9x.
+ See comment in cwdstuff::set below. */
+ if (!wincap.can_open_directories ())
+ SetCurrentDirectory (windows_system_directory);
+ else
+ close_user_proc_parms_cwd_handle ();
}
cwd_lock.release ();
}
@@ -4172,12 +4205,14 @@ cwdstuff::init ()
void
cwdstuff::keep_in_sync (bool val)
{
- sync = val;
- SetCurrentDirectory (val ? win32 : windows_system_directory);
+ if (!wincap.can_open_directories ())
+ {
+ sync = val;
+ SetCurrentDirectory (val ? win32 : windows_system_directory);
+ }
}
-/* Get initial cwd. Should only be called once in a
- process tree. */
+/* Get initial cwd. Should only be called once in a process tree. */
bool
cwdstuff::get_initial ()
{
@@ -4209,7 +4244,7 @@ cwdstuff::set (const char *win32_cwd, const char *posix_cwd, bool doit)
/* If a Cygwin application called cygwin_internal(CW_SYNC_WINENV),
then it's about to call native Windows functions. This also
sets the keep_in_sync flag so that we actually chdir into the
- native directory to avoid confusion. */
+ native directory on 9x to avoid confusion. */
if (!SetCurrentDirectory (win32_cwd))
{
__seterrno ();
@@ -4218,13 +4253,20 @@ cwdstuff::set (const char *win32_cwd, const char *posix_cwd, bool doit)
}
else
{
- /* Check if we *could* chdir, if we actually would.
-
- Why don't we actually chdir? For two reasons:
+ /* We don't actually chdir on 9x but stay in the system dir.
+
+ On NT we utilize the user parameter block. The directory is
+ stored manually, but the handle to the directory is always
+ closed and set to NULL. This way the directory isn't blocked
+ even if it's the cwd of a Cygwin process.
+
+ Why the hassle?
+
- A process has always an open handle to the current working
directory which disallows manipulating this directory.
- POSIX allows to remove a directory if the permissions are
- ok. The fact that its the cwd of some process doesn't matter.
+ POSIX allows to remove a directory if the permissions are ok.
+ The fact that its the cwd of some process doesn't matter.
+
- SetCurrentDirectory fails for directories with strict
permissions even for processes with the SE_BACKUP_NAME
privilege enabled. The reason is apparently that
@@ -4243,7 +4285,7 @@ cwdstuff::set (const char *win32_cwd, const char *posix_cwd, bool doit)
}
if (wincap.can_open_directories ())
{
- HANDLE h = CreateFile (win32_cwd, GENERIC_READ,
+ HANDLE h = CreateFile (win32_cwd, FILE_TRAVERSE,
wincap.shared (), NULL, OPEN_EXISTING,
FILE_FLAG_BACKUP_SEMANTICS, NULL);
if (h == INVALID_HANDLE_VALUE)
@@ -4251,6 +4293,23 @@ cwdstuff::set (const char *win32_cwd, const char *posix_cwd, bool doit)
__seterrno ();
goto out;
}
+ ULONG len = strlen (win32_cwd);
+ ANSI_STRING as = {len, len + 2, (PCHAR) alloca (len + 2)};
+ strcpy (as.Buffer, win32_cwd);
+ if (as.Buffer[len - 1] != '\\')
+ {
+ strcpy (as.Buffer + len, "\\");
+ ++as.Length;
+ }
+ if (current_codepage == ansi_cp)
+ RtlAnsiStringToUnicodeString (
+ &get_user_proc_parms ()->CurrentDirectoryName,
+ &as, FALSE);
+ else
+ RtlOemStringToUnicodeString (
+ &get_user_proc_parms ()->CurrentDirectoryName,
+ &as, FALSE);
+ close_user_proc_parms_cwd_handle ();
CloseHandle (h);
}
}