server: Check that the prefix type can support the client architecture.
This commit is contained in:
parent
bbc03d5172
commit
ac69fcb14f
|
@ -908,11 +908,8 @@ static void start_wineboot( HANDLE handles[2] )
|
|||
{
|
||||
static const WCHAR wineboot[] = {'\\','w','i','n','e','b','o','o','t','.','e','x','e',0};
|
||||
static const WCHAR args[] = {' ','-','-','i','n','i','t',0};
|
||||
const DWORD expected_type = (sizeof(void*) > sizeof(int) || is_wow64) ?
|
||||
SCS_64BIT_BINARY : SCS_32BIT_BINARY;
|
||||
STARTUPINFOW si;
|
||||
PROCESS_INFORMATION pi;
|
||||
DWORD type;
|
||||
void *redir;
|
||||
WCHAR app[MAX_PATH];
|
||||
WCHAR cmdline[MAX_PATH + (sizeof(wineboot) + sizeof(args)) / sizeof(WCHAR)];
|
||||
|
@ -928,17 +925,6 @@ static void start_wineboot( HANDLE handles[2] )
|
|||
lstrcatW( app, wineboot );
|
||||
|
||||
Wow64DisableWow64FsRedirection( &redir );
|
||||
if (GetBinaryTypeW( app, &type ) && type != expected_type)
|
||||
{
|
||||
if (type == SCS_64BIT_BINARY)
|
||||
MESSAGE( "wine: '%s' is a 64-bit prefix, it cannot be used with 32-bit Wine.\n",
|
||||
wine_get_config_dir() );
|
||||
else
|
||||
MESSAGE( "wine: '%s' is a 32-bit prefix, it cannot be used with %s Wine.\n",
|
||||
wine_get_config_dir(), is_wow64 ? "wow64" : "64-bit" );
|
||||
ExitProcess( 1 );
|
||||
}
|
||||
|
||||
strcpyW( cmdline, app );
|
||||
strcatW( cmdline, args );
|
||||
if (CreateProcessW( app, cmdline, NULL, NULL, FALSE, DETACHED_PROCESS, NULL, NULL, &si, &pi ))
|
||||
|
|
|
@ -1039,6 +1039,7 @@ NTSTATUS server_init_process_done(void)
|
|||
*/
|
||||
size_t server_init_thread( void *entry_point )
|
||||
{
|
||||
static const int is_win64 = (sizeof(void *) > sizeof(int));
|
||||
int ret;
|
||||
int reply_pipe[2];
|
||||
struct sigaction sig_act;
|
||||
|
@ -1083,20 +1084,23 @@ size_t server_init_thread( void *entry_point )
|
|||
}
|
||||
SERVER_END_REQ;
|
||||
|
||||
#ifndef _WIN64
|
||||
is_wow64 = (server_cpus & (1 << CPU_x86_64)) != 0;
|
||||
#endif
|
||||
is_wow64 = !is_win64 && (server_cpus & (1 << CPU_x86_64)) != 0;
|
||||
ntdll_get_thread_data()->wow64_redir = is_wow64;
|
||||
|
||||
if (ret)
|
||||
switch (ret)
|
||||
{
|
||||
if (ret == STATUS_NOT_SUPPORTED)
|
||||
{
|
||||
static const char * const cpu_arch[] = { "x86", "x86_64", "Alpha", "PowerPC", "Sparc" };
|
||||
server_protocol_error( "the running wineserver doesn't support the %s architecture.\n",
|
||||
cpu_arch[client_cpu] );
|
||||
}
|
||||
else server_protocol_error( "init_thread failed with status %x\n", ret );
|
||||
case STATUS_SUCCESS:
|
||||
return info_size;
|
||||
case STATUS_NOT_REGISTRY_FILE:
|
||||
fatal_error( "'%s' is a 32-bit installation, it cannot support 64-bit applications.\n",
|
||||
wine_get_config_dir() );
|
||||
case STATUS_NOT_SUPPORTED:
|
||||
if (is_win64)
|
||||
fatal_error( "wineserver is 32-bit, it cannot support 64-bit applications.\n" );
|
||||
else
|
||||
fatal_error( "'%s' is a 64-bit installation, it cannot be used with a 32-bit wineserver.\n",
|
||||
wine_get_config_dir() );
|
||||
default:
|
||||
server_protocol_error( "init_thread failed with status %x\n", ret );
|
||||
}
|
||||
return info_size;
|
||||
}
|
||||
|
|
|
@ -186,6 +186,7 @@ extern int get_page_size(void);
|
|||
|
||||
/* registry functions */
|
||||
|
||||
extern unsigned int get_prefix_cpu_mask(void);
|
||||
extern void init_registry(void);
|
||||
extern void flush_registry(void);
|
||||
|
||||
|
|
|
@ -1641,6 +1641,34 @@ static WCHAR *format_user_registry_path( const SID *sid, struct unicode_str *pat
|
|||
return p;
|
||||
}
|
||||
|
||||
/* get the cpu architectures that can be supported in the current prefix */
|
||||
unsigned int get_prefix_cpu_mask(void)
|
||||
{
|
||||
/* Allowed server/client/prefix combinations:
|
||||
*
|
||||
* prefix
|
||||
* 32 64
|
||||
* server +------+------+ client
|
||||
* | ok | fail | 32
|
||||
* 32 +------+------+---
|
||||
* | fail | fail | 64
|
||||
* ---+------+------+---
|
||||
* | ok | ok | 32
|
||||
* 64 +------+------+---
|
||||
* | fail | ok | 64
|
||||
* ---+------+------+---
|
||||
*/
|
||||
switch (prefix_type)
|
||||
{
|
||||
case PREFIX_64BIT:
|
||||
/* 64-bit prefix requires 64-bit server */
|
||||
return sizeof(void *) > sizeof(int) ? ~0 : 0;
|
||||
case PREFIX_32BIT:
|
||||
default:
|
||||
return ~CPU_64BIT_MASK; /* only 32-bit cpus supported on 32-bit prefix */
|
||||
}
|
||||
}
|
||||
|
||||
/* registry initialisation */
|
||||
void init_registry(void)
|
||||
{
|
||||
|
|
|
@ -1098,6 +1098,7 @@ DECL_HANDLER(new_thread)
|
|||
/* initialize a new thread */
|
||||
DECL_HANDLER(init_thread)
|
||||
{
|
||||
unsigned int prefix_cpu_mask = get_prefix_cpu_mask();
|
||||
struct process *process = current->process;
|
||||
int reply_fd = thread_get_inflight_fd( current, req->reply_fd );
|
||||
int wait_fd = thread_get_inflight_fd( current, req->wait_fd );
|
||||
|
@ -1134,9 +1135,12 @@ DECL_HANDLER(init_thread)
|
|||
|
||||
if (!process->peb) /* first thread, initialize the process too */
|
||||
{
|
||||
if (!CPU_FLAG(req->cpu) || !(supported_cpus & CPU_FLAG(req->cpu)))
|
||||
if (!CPU_FLAG(req->cpu) || !(supported_cpus & prefix_cpu_mask & CPU_FLAG(req->cpu)))
|
||||
{
|
||||
set_error( STATUS_NOT_SUPPORTED );
|
||||
if (!(supported_cpus & CPU_64BIT_MASK))
|
||||
set_error( STATUS_NOT_SUPPORTED );
|
||||
else
|
||||
set_error( STATUS_NOT_REGISTRY_FILE ); /* server supports it but not the prefix */
|
||||
return;
|
||||
}
|
||||
process->unix_pid = current->unix_pid;
|
||||
|
@ -1163,7 +1167,7 @@ DECL_HANDLER(init_thread)
|
|||
reply->tid = get_thread_id( current );
|
||||
reply->version = SERVER_PROTOCOL_VERSION;
|
||||
reply->server_start = server_start_time;
|
||||
reply->all_cpus = supported_cpus;
|
||||
reply->all_cpus = supported_cpus & prefix_cpu_mask;
|
||||
return;
|
||||
|
||||
error:
|
||||
|
|
Loading…
Reference in New Issue