ntdll: Allocate the buffer in the caller for wine_unix_to_nt_file_name().
Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
parent
5ebdeaaa37
commit
6f862a1ad8
|
@ -312,36 +312,38 @@ char * CDECL wine_get_unix_file_name( LPCWSTR dosW )
|
|||
WCHAR * CDECL wine_get_dos_file_name( LPCSTR str )
|
||||
{
|
||||
UNICODE_STRING nt_name;
|
||||
ANSI_STRING unix_name;
|
||||
NTSTATUS status;
|
||||
WCHAR *buffer;
|
||||
DWORD len;
|
||||
SIZE_T len = strlen(str) + 1;
|
||||
|
||||
if (str[0] != '/') /* relative path name */
|
||||
{
|
||||
len = strlen( str ) + 1;
|
||||
if (!(buffer = RtlAllocateHeap( GetProcessHeap(), 0, len * sizeof(WCHAR) ))) return NULL;
|
||||
MultiByteToWideChar( CP_UNIXCP, 0, str, len, buffer, len );
|
||||
status = RtlDosPathNameToNtPathName_U_WithStatus( buffer, &nt_name, NULL, NULL );
|
||||
RtlFreeHeap( GetProcessHeap(), 0, buffer );
|
||||
if (!set_ntstatus( status )) return NULL;
|
||||
buffer = nt_name.Buffer;
|
||||
len = nt_name.Length / sizeof(WCHAR) + 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
RtlInitAnsiString( &unix_name, str );
|
||||
status = wine_unix_to_nt_file_name( &unix_name, &nt_name );
|
||||
len += 8; /* \??\unix prefix */
|
||||
if (!(buffer = HeapAlloc( GetProcessHeap(), 0, len * sizeof(WCHAR) ))) return NULL;
|
||||
if (!set_ntstatus( wine_unix_to_nt_file_name( str, buffer, &len )))
|
||||
{
|
||||
HeapFree( GetProcessHeap(), 0, buffer );
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
if (!set_ntstatus( status )) return NULL;
|
||||
if (nt_name.Buffer[5] == ':')
|
||||
if (buffer[5] == ':')
|
||||
{
|
||||
/* get rid of the \??\ prefix */
|
||||
/* FIXME: should implement RtlNtPathNameToDosPathName and use that instead */
|
||||
len = nt_name.Length - 4 * sizeof(WCHAR);
|
||||
memmove( nt_name.Buffer, nt_name.Buffer + 4, len );
|
||||
nt_name.Buffer[len / sizeof(WCHAR)] = 0;
|
||||
memmove( buffer, buffer + 4, (len - 4) * sizeof(WCHAR) );
|
||||
}
|
||||
else
|
||||
nt_name.Buffer[1] = '\\';
|
||||
return nt_name.Buffer;
|
||||
else buffer[1] = '\\';
|
||||
return buffer;
|
||||
}
|
||||
|
||||
/*************************************************************************
|
||||
|
|
|
@ -1605,4 +1605,4 @@
|
|||
|
||||
# Filesystem
|
||||
@ cdecl wine_nt_to_unix_file_name(ptr ptr ptr long)
|
||||
@ cdecl wine_unix_to_nt_file_name(ptr ptr)
|
||||
@ cdecl wine_unix_to_nt_file_name(str ptr ptr)
|
||||
|
|
|
@ -545,26 +545,34 @@ static ULONG get_full_path_helper(LPCWSTR name, LPWSTR buffer, ULONG size)
|
|||
if (name[0] == '/') /* may be a Unix path */
|
||||
{
|
||||
char *unix_name;
|
||||
ANSI_STRING unix_str;
|
||||
UNICODE_STRING nt_str;
|
||||
WCHAR *nt_str;
|
||||
SIZE_T buflen;
|
||||
NTSTATUS status;
|
||||
|
||||
unix_name = RtlAllocateHeap( GetProcessHeap(), 0, 3 * wcslen(name) + 1 );
|
||||
ntdll_wcstoumbs( name, wcslen(name) + 1, unix_name, 3 * wcslen(name) + 1, FALSE );
|
||||
RtlInitAnsiString( &unix_str, unix_name );
|
||||
unix_funcs->unix_to_nt_file_name( &unix_str, &nt_str );
|
||||
RtlFreeAnsiString( &unix_str );
|
||||
if (nt_str.Length > 5 * sizeof(WCHAR) && nt_str.Buffer[5] == ':')
|
||||
buflen = strlen(unix_name) + 10;
|
||||
for (;;)
|
||||
{
|
||||
reqsize = nt_str.Length - 3 * sizeof(WCHAR);
|
||||
if (!(nt_str = RtlAllocateHeap( GetProcessHeap(), 0, buflen * sizeof(WCHAR) ))) break;
|
||||
status = unix_funcs->unix_to_nt_file_name( unix_name, nt_str, &buflen );
|
||||
if (status != STATUS_BUFFER_TOO_SMALL) break;
|
||||
RtlFreeHeap( GetProcessHeap(), 0, nt_str );
|
||||
}
|
||||
RtlFreeHeap( GetProcessHeap(), 0, unix_name );
|
||||
if (!status && buflen > 6 && nt_str[5] == ':')
|
||||
{
|
||||
reqsize = (buflen - 4) * sizeof(WCHAR);
|
||||
if (reqsize <= size)
|
||||
{
|
||||
memcpy( buffer, nt_str.Buffer + 4, reqsize );
|
||||
memcpy( buffer, nt_str + 4, reqsize );
|
||||
collapse_path( buffer, 3 );
|
||||
reqsize -= sizeof(WCHAR);
|
||||
}
|
||||
RtlFreeUnicodeString( &nt_str );
|
||||
RtlFreeHeap( GetProcessHeap(), 0, nt_str );
|
||||
goto done;
|
||||
}
|
||||
RtlFreeHeap( GetProcessHeap(), 0, nt_str );
|
||||
}
|
||||
if (cd->Buffer[1] == ':')
|
||||
{
|
||||
|
@ -889,12 +897,7 @@ NTSTATUS WINAPI RtlSetCurrentDirectory_U(const UNICODE_STRING* dir)
|
|||
/******************************************************************
|
||||
* wine_unix_to_nt_file_name (NTDLL.@) Not a Windows API
|
||||
*/
|
||||
NTSTATUS CDECL wine_unix_to_nt_file_name( const ANSI_STRING *name, UNICODE_STRING *nt )
|
||||
NTSTATUS CDECL wine_unix_to_nt_file_name( const char *name, WCHAR *buffer, SIZE_T *size )
|
||||
{
|
||||
unsigned int lenA = name->Length;
|
||||
const char *path = name->Buffer;
|
||||
|
||||
if (!lenA) return STATUS_INVALID_PARAMETER;
|
||||
if (path[0] != '/') return STATUS_INVALID_PARAMETER; /* relative path not supported */
|
||||
return unix_funcs->unix_to_nt_file_name( name, nt );
|
||||
return unix_funcs->unix_to_nt_file_name( name, buffer, size );
|
||||
}
|
||||
|
|
|
@ -3482,11 +3482,21 @@ NTSTATUS unix_to_nt_file_name( const char *name, WCHAR **nt )
|
|||
/******************************************************************
|
||||
* wine_unix_to_nt_file_name
|
||||
*/
|
||||
NTSTATUS CDECL wine_unix_to_nt_file_name( const ANSI_STRING *name, UNICODE_STRING *nt )
|
||||
NTSTATUS CDECL wine_unix_to_nt_file_name( const char *name, WCHAR *buffer, SIZE_T *size )
|
||||
{
|
||||
WCHAR *nt_name = NULL;
|
||||
NTSTATUS status = unix_to_nt_file_name( name->Buffer, &nt_name );
|
||||
if (nt_name) RtlInitUnicodeString( nt, nt_name );
|
||||
NTSTATUS status;
|
||||
|
||||
if (name[0] != '/') return STATUS_INVALID_PARAMETER; /* relative paths are not supported */
|
||||
|
||||
status = unix_to_nt_file_name( name, &nt_name );
|
||||
if (nt_name)
|
||||
{
|
||||
if (*size > wcslen(nt_name)) wcscpy( buffer, nt_name );
|
||||
else status = STATUS_BUFFER_TOO_SMALL;
|
||||
*size = wcslen(nt_name) + 1;
|
||||
RtlFreeHeap( GetProcessHeap(), 0, nt_name );
|
||||
}
|
||||
return status;
|
||||
}
|
||||
|
||||
|
|
|
@ -28,7 +28,7 @@ struct msghdr;
|
|||
struct _DISPATCHER_CONTEXT;
|
||||
|
||||
/* increment this when you change the function table */
|
||||
#define NTDLL_UNIXLIB_VERSION 73
|
||||
#define NTDLL_UNIXLIB_VERSION 74
|
||||
|
||||
struct unix_funcs
|
||||
{
|
||||
|
@ -334,7 +334,7 @@ struct unix_funcs
|
|||
/* file functions */
|
||||
NTSTATUS (CDECL *nt_to_unix_file_name)( const UNICODE_STRING *nameW, char *nameA, SIZE_T *size,
|
||||
UINT disposition );
|
||||
NTSTATUS (CDECL *unix_to_nt_file_name)( const ANSI_STRING *name, UNICODE_STRING *nt );
|
||||
NTSTATUS (CDECL *unix_to_nt_file_name)( const char *name, WCHAR *buffer, SIZE_T *size );
|
||||
void (CDECL *set_show_dot_files)( BOOL enable );
|
||||
|
||||
/* loader functions */
|
||||
|
|
|
@ -3373,7 +3373,7 @@ NTSYSAPI void WINAPI TpWaitForWork(TP_WORK *,BOOL);
|
|||
|
||||
NTSYSAPI NTSTATUS CDECL wine_nt_to_unix_file_name( const UNICODE_STRING *nameW, char *nameA, SIZE_T *size,
|
||||
UINT disposition );
|
||||
NTSYSAPI NTSTATUS CDECL wine_unix_to_nt_file_name( const ANSI_STRING *name, UNICODE_STRING *nt );
|
||||
NTSYSAPI NTSTATUS CDECL wine_unix_to_nt_file_name( const char *name, WCHAR *buffer, SIZE_T *size );
|
||||
|
||||
|
||||
/***********************************************************************
|
||||
|
|
Loading…
Reference in New Issue