cs Windows: fill in GUI mode for GRacket
Still need to create console on demand.
This commit is contained in:
parent
a24c6fe4f9
commit
b5084977c0
2
Makefile
2
Makefile
|
@ -385,7 +385,7 @@ win32-racket-then-cs:
|
|||
$(MAKE) win32-base PKGS="" $(WIN32_CS_COPY_ARGS_EXCEPT_PKGS_SUT) WIN32_BUILD_LEVEL="$(WIN32_BUILD_LEVEL)"
|
||||
$(MAKE) win32-just-cs RACKET=$(WIN32_PLAIN_RACKET) $(WIN32_CS_COPY_ARGS_BOOT)
|
||||
|
||||
CSBUILD_ARGUMENTS = --scheme-dir "$(SCHEME_SRC)" \
|
||||
CSBUILD_ARGUMENTS = --scheme-dir "$(SCHEME_SRC)" --pull \
|
||||
--racketcs-suffix "$(RACKETCS_SUFFIX)" \
|
||||
--boot-mode "$(SETUP_BOOT_MODE)" \
|
||||
--extra-repos-base "$(EXTRA_REPOS_BASE)" \
|
||||
|
|
|
@ -19,7 +19,7 @@ RUMBLE_UNSAFE_COMP = --unsafe
|
|||
COMPILE_FILE = $(SCHEME) --script compile-file.ss $(UNSAFE_COMP) $(COMPRESS_COMP) $(DEBUG_COMP) --dest "$(BUILDDIR)"
|
||||
COMPILE_FILE_DEPS = compile-file.ss include.ss place-register.ss
|
||||
|
||||
RACKET_SETUP_ARGS = ../../bin/racket ../collects ../etc 0 true false
|
||||
RACKET_SETUP_ARGS = ../../bin/racket ../collects ../etc 0 true false 0 ""
|
||||
|
||||
PRIMITIVES_TABLES = primitive/kernel.ss primitive/unsafe.ss primitive/flfxnum.ss \
|
||||
primitive/paramz.ss primitive/extfl.ss primitive/network.ss \
|
||||
|
|
|
@ -88,7 +88,8 @@ void racket_boot(int argc, char **argv, char *self,
|
|||
char *boot_exe, long segment_offset,
|
||||
char *coldir, char *configdir,
|
||||
int pos1, int pos2, int pos3,
|
||||
int cs_compiled_subdir, int is_gui)
|
||||
int cs_compiled_subdir, int is_gui,
|
||||
int wm_is_gracket, const char *gracket_guid)
|
||||
/* exe argument already stripped from argv */
|
||||
{
|
||||
#if !defined(RACKET_USE_FRAMEWORK) || !defined(RACKET_AS_BOOT)
|
||||
|
@ -134,11 +135,14 @@ void racket_boot(int argc, char **argv, char *self,
|
|||
{
|
||||
ptr l = Snil;
|
||||
int i;
|
||||
char segment_offset_s[32];
|
||||
char segment_offset_s[32], wm_is_gracket_s[32];
|
||||
|
||||
for (i = argc; i--; ) {
|
||||
l = Scons(Sbytevector(argv[i]), l);
|
||||
}
|
||||
l = Scons(Sbytevector(gracket_guid), l);
|
||||
sprintf(wm_is_gracket_s, "%ld", wm_is_gracket);
|
||||
l = Scons(Sbytevector(wm_is_gracket_s), l);
|
||||
l = Scons(Sbytevector(is_gui ? "true" : "false"), l);
|
||||
l = Scons(Sbytevector(cs_compiled_subdir ? "true" : "false"), l);
|
||||
sprintf(segment_offset_s, "%ld", segment_offset);
|
||||
|
|
|
@ -2,10 +2,12 @@ BOOT_EXTERN void racket_boot(int argc, char **argv, char *self,
|
|||
char *boot_exe, long segment_offset,
|
||||
char *coldir, char *configdir,
|
||||
int pos1, int pos2, int pos3,
|
||||
int cs_compiled_subdir, int is_gui);
|
||||
int cs_compiled_subdir, int is_gui,
|
||||
int wm_is_gracket, const char *gracket_guid);
|
||||
|
||||
typedef void (*racket_boot_t)(int argc, char **argv, char *self,
|
||||
char* boot_exe, long segment_offset,
|
||||
char *coldir, char *configdir,
|
||||
int pos1, int pos2, int pos3,
|
||||
int cs_compiled_subdir, int is_gui);
|
||||
int cs_compiled_subdir, int is_gui,
|
||||
int wm_is_gracket, const char *gracket_guid);
|
||||
|
|
|
@ -9,6 +9,17 @@ static void pre_filter_cmdline_arguments(int *argc, char ***argv);
|
|||
# ifndef INITIAL_COLLECTS_DIRECTORY
|
||||
# define INITIAL_COLLECTS_DIRECTORY "../collects"
|
||||
# endif
|
||||
# ifndef INITIAL_CONFIG_DIRECTORY
|
||||
# define INITIAL_CONFIG_DIRECTORY "../etc"
|
||||
# endif
|
||||
|
||||
/* Hack: overwrite "y" with "n" in binary to disable checking for another
|
||||
instance of the same app. */
|
||||
char *check_for_another = "yes, please check for another";
|
||||
|
||||
# include <Windows.h>
|
||||
# include "../start/win_single.inc"
|
||||
# define CHECK_SINGLE_INSTANCE
|
||||
#endif
|
||||
|
||||
#include "main.c"
|
||||
|
|
|
@ -125,9 +125,8 @@ static long find_boot_section(char *me)
|
|||
}
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef WIN32
|
||||
static char *path_to_utf8(wchar_t *p)
|
||||
static char *string_to_utf8(wchar_t *p)
|
||||
{
|
||||
char *r;
|
||||
int len;
|
||||
|
@ -141,7 +140,7 @@ static char *path_to_utf8(wchar_t *p)
|
|||
|
||||
static char *get_self_path()
|
||||
{
|
||||
return path_to_utf8(get_self_executable_path());
|
||||
return string_to_utf8(get_self_executable_path());
|
||||
}
|
||||
|
||||
static int scheme_utf8_encode(unsigned int *path, int zero_offset, int len,
|
||||
|
@ -149,6 +148,8 @@ static int scheme_utf8_encode(unsigned int *path, int zero_offset, int len,
|
|||
{
|
||||
return WideCharToMultiByte(CP_UTF8, 0, (wchar_t *)path, len, dest, dest_len, NULL, NULL);
|
||||
}
|
||||
|
||||
# include "../start/parse_cmdl.inc"
|
||||
#endif
|
||||
|
||||
#ifdef NO_GET_SEGMENT_OFFSET
|
||||
|
@ -162,7 +163,9 @@ static long get_segment_offset()
|
|||
# define do_pre_filter_cmdline_arguments(argc, argv) /* empty */
|
||||
#endif
|
||||
|
||||
int main(int argc, char **argv)
|
||||
static int bytes_main(int argc, char **argv,
|
||||
/* for Windows GUI mode */
|
||||
int wm_is_gracket, const char *gracket_guid)
|
||||
{
|
||||
char *self, *boot_exe, *prog = argv[0], *sprog = NULL;
|
||||
int pos1, pos2, pos3;
|
||||
|
@ -176,8 +179,10 @@ int main(int argc, char **argv)
|
|||
|
||||
do_pre_filter_cmdline_arguments(&argc, &argv);
|
||||
|
||||
argc--;
|
||||
argv++;
|
||||
if (argc) {
|
||||
argc--;
|
||||
argv++;
|
||||
}
|
||||
|
||||
extract_built_in_arguments(&prog, &sprog, &argc, &argv);
|
||||
segment_offset = get_segment_offset();
|
||||
|
@ -187,7 +192,7 @@ int main(int argc, char **argv)
|
|||
#ifdef WIN32
|
||||
# define racket_boot racket_boot_p
|
||||
dll_path = load_delayed_dll_x(NULL, "libracketcsxxxxxxx.dll", &dll);
|
||||
boot_exe = path_to_utf8(dll_path);
|
||||
boot_exe = string_to_utf8(dll_path);
|
||||
racket_boot_p = (racket_boot_t)GetProcAddress(dll, "racket_boot");
|
||||
#else
|
||||
boot_exe = self;
|
||||
|
@ -213,7 +218,44 @@ int main(int argc, char **argv)
|
|||
boot_exe, segment_offset,
|
||||
extract_coldir(), extract_configdir(),
|
||||
pos1, pos2, pos3,
|
||||
CS_COMPILED_SUBDIR, RACKET_IS_GUI);
|
||||
CS_COMPILED_SUBDIR, RACKET_IS_GUI,
|
||||
wm_is_gracket, gracket_guid);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
#if defined(WIN32) && defined(CHECK_SINGLE_INSTANCE)
|
||||
int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR ignored, int nCmdShow)
|
||||
{
|
||||
int argc;
|
||||
char **argv;
|
||||
char *normalized_path;
|
||||
int wm = 0;
|
||||
const char *guid = "";
|
||||
|
||||
argv = cmdline_to_argv(&argc, &normalized_path);
|
||||
|
||||
if (CheckSingleInstance(normalized_path, argv))
|
||||
return 0;
|
||||
wm = wm_is_gracket;
|
||||
guid = GRACKET_GUID;
|
||||
|
||||
return bytes_main(argc, argv, wm, guid);
|
||||
}
|
||||
#elif defined(WIN32)
|
||||
int wmain(int argc, wchar_t **wargv)
|
||||
{
|
||||
int i;
|
||||
char **argv = malloc(argc * sizeof(char*));
|
||||
|
||||
for (i = 0; i < argc; i++) {
|
||||
argv[i] = string_to_utf8(wargv[i]);
|
||||
}
|
||||
|
||||
return bytes_main(argc, argv, 0, "");
|
||||
}
|
||||
#else
|
||||
int main(int argc, char **argv) {
|
||||
return bytes_main(argc, argv, 0, "");
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -55,9 +55,14 @@
|
|||
s))
|
||||
the-command-line-arguments/maybe-bytes))
|
||||
|
||||
(define builtin-argc 8)
|
||||
(seq
|
||||
(unless (>= (length the-command-line-arguments) 6)
|
||||
(error 'racket "expected `self`, `collects`, and `libs` paths plus `segment-offset`, `cs-compiled-subdir?`, and `is-gui?` to start"))
|
||||
(unless (>= (length the-command-line-arguments) builtin-argc)
|
||||
(error 'racket (string-append
|
||||
"expected `self`, `collects`, and `libs` paths"
|
||||
" plus `segment-offset`, `cs-compiled-subdir?`, `is-gui?`,"
|
||||
" `wm-is-gracket`, and `gracket-guid`"
|
||||
" to start")))
|
||||
(set-exec-file! (path->complete-path (car the-command-line-arguments))))
|
||||
(define init-collects-dir (let ([s (cadr the-command-line-arguments)])
|
||||
(if (equal? s "") 'disable (string->path s))))
|
||||
|
@ -66,10 +71,18 @@
|
|||
(define segment-offset (#%string->number (list-ref the-command-line-arguments 3)))
|
||||
(define cs-compiled-subdir? (string=? "true" (list-ref the-command-line-arguments 4)))
|
||||
(define gracket? (string=? "true" (list-ref the-command-line-arguments 5)))
|
||||
(define wm-is-gracket (string->number (list-ref the-command-line-arguments 6)))
|
||||
(define gracket-guid (list-ref the-command-line-arguments 7))
|
||||
|
||||
(seq
|
||||
(when (foreign-entry? "racket_exit")
|
||||
(#%exit-handler (foreign-procedure "racket_exit" (int) void))))
|
||||
(#%exit-handler (foreign-procedure "racket_exit" (int) void)))
|
||||
|
||||
;; For Windows:
|
||||
(unsafe-register-process-global (string->bytes/utf-8 "PLT_WM_IS_GRACKET")
|
||||
(ptr-add #f wm-is-gracket))
|
||||
(unsafe-register-process-global (string->bytes/utf-8 "PLT_GRACKET_GUID")
|
||||
(bytes-append (string->bytes/utf-8 gracket-guid) #vu8(0))))
|
||||
|
||||
(define compiled-file-paths
|
||||
(list (string->path (cond
|
||||
|
@ -227,7 +240,7 @@
|
|||
(define remaining-command-line-arguments '#())
|
||||
|
||||
(seq
|
||||
(let flags-loop ([args (list-tail the-command-line-arguments 6)]
|
||||
(let flags-loop ([args (list-tail the-command-line-arguments builtin-argc)]
|
||||
[saw (hasheq)])
|
||||
;; An element of `args` can become `(cons _arg _within-arg)`
|
||||
;; due to splitting multiple flags with a single "-"
|
||||
|
|
|
@ -412,175 +412,7 @@ static void MrEdExit(int v)
|
|||
START_XFORM_SKIP;
|
||||
# endif
|
||||
|
||||
/* ---------------------------------------- */
|
||||
/* single-instance detection */
|
||||
/* ---------------------------------------- */
|
||||
|
||||
static char *CreateUniqueName()
|
||||
{
|
||||
char desktop[MAX_PATH], session[32], *together;
|
||||
int dlen, slen;
|
||||
|
||||
{
|
||||
// Name should be desktop unique, so add current desktop name
|
||||
HDESK hDesk;
|
||||
ULONG cchDesk = MAX_PATH - 1;
|
||||
|
||||
hDesk = GetThreadDesktop(GetCurrentThreadId());
|
||||
|
||||
if (!GetUserObjectInformation( hDesk, UOI_NAME, desktop, cchDesk, &cchDesk))
|
||||
desktop[0] = 0;
|
||||
else
|
||||
desktop[MAX_PATH - 1] = 0;
|
||||
}
|
||||
|
||||
{
|
||||
// Name should be session unique, so add current session id
|
||||
HANDLE hToken = NULL;
|
||||
// Try to open the token (fails on Win9x) and check necessary buffer size
|
||||
if (OpenProcessToken(GetCurrentProcess(), TOKEN_QUERY, &hToken)) {
|
||||
DWORD cbBytes = 0;
|
||||
|
||||
if(!GetTokenInformation( hToken, TokenStatistics, NULL, cbBytes, &cbBytes )
|
||||
&& GetLastError() == ERROR_INSUFFICIENT_BUFFER) {
|
||||
PTOKEN_STATISTICS pTS;
|
||||
|
||||
pTS = (PTOKEN_STATISTICS)malloc(cbBytes);
|
||||
|
||||
if(GetTokenInformation(hToken, TokenStatistics, (LPVOID)pTS, cbBytes, &cbBytes)) {
|
||||
sprintf(session, "-%08x%08x-",
|
||||
pTS->AuthenticationId.HighPart,
|
||||
pTS->AuthenticationId.LowPart);
|
||||
} else
|
||||
session[0] = 0;
|
||||
free(pTS);
|
||||
} else {
|
||||
session[0] = 0;
|
||||
}
|
||||
} else
|
||||
session[0] = 0;
|
||||
}
|
||||
|
||||
dlen = strlen(desktop);
|
||||
slen = strlen(session);
|
||||
together = (char *)malloc(slen + dlen + 1);
|
||||
memcpy(together, desktop, dlen);
|
||||
memcpy(together + dlen, session, slen);
|
||||
together[dlen + slen] = 0;
|
||||
|
||||
return together;
|
||||
}
|
||||
|
||||
#define GRACKET_GUID "B2261834-D535-44dd-8511-A26FC8F97DD0"
|
||||
|
||||
static int wm_is_gracket;
|
||||
|
||||
static BOOL CALLBACK CheckWindow(HWND wnd, LPARAM param)
|
||||
{
|
||||
int i, len, gl;
|
||||
DWORD w;
|
||||
char **argv, *v;
|
||||
COPYDATASTRUCT cd;
|
||||
DWORD_PTR result;
|
||||
LRESULT ok;
|
||||
|
||||
ok = SendMessageTimeout(wnd, wm_is_gracket,
|
||||
0, 0,
|
||||
SMTO_BLOCK |
|
||||
SMTO_ABORTIFHUNG,
|
||||
200,
|
||||
&result);
|
||||
|
||||
printf("try %p result %d\n", wnd, result);
|
||||
|
||||
if (ok == 0)
|
||||
return TRUE; /* ignore and continue */
|
||||
if ((intptr_t)result == 79) {
|
||||
/* found it */
|
||||
} else
|
||||
return TRUE; /* continue search */
|
||||
|
||||
/* wnd is owned by another instance of this application */
|
||||
|
||||
SetForegroundWindow(wnd);
|
||||
if (IsIconic(wnd))
|
||||
ShowWindow(wnd, SW_RESTORE);
|
||||
|
||||
argv = (char **)param;
|
||||
|
||||
len = gl = strlen(GRACKET_GUID);
|
||||
len += 4 + sizeof(DWORD);
|
||||
for (i = 1; argv[i]; i++) {
|
||||
len += sizeof(DWORD) + strlen(argv[i]);
|
||||
}
|
||||
w = i - 1;
|
||||
|
||||
v = (char *)malloc(len);
|
||||
memcpy(v, GRACKET_GUID, gl);
|
||||
memcpy(v + gl, "OPEN", 4);
|
||||
memcpy(v + gl + 4, &w, sizeof(DWORD));
|
||||
len = gl + 4 + sizeof(DWORD);
|
||||
for (i = 1; argv[i]; i++) {
|
||||
w = strlen(argv[i]);
|
||||
memcpy(v + len, &w, sizeof(DWORD));
|
||||
len += sizeof(DWORD);
|
||||
memcpy(v + len, argv[i], w);
|
||||
len += w;
|
||||
}
|
||||
|
||||
cd.dwData = 79;
|
||||
cd.cbData = len;
|
||||
cd.lpData = v;
|
||||
|
||||
SendMessage(wnd, WM_COPYDATA, (WPARAM)wnd, (LPARAM)&cd);
|
||||
|
||||
free(v);
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
static int CheckSingleInstance(char *normalized_path, char **argv)
|
||||
{
|
||||
/* Check for an existing instance: */
|
||||
if (check_for_another[0] != 'n') {
|
||||
int alreadyrunning;
|
||||
HANDLE mutex;
|
||||
int j, l, i;
|
||||
char *a, *b;
|
||||
|
||||
/* This mutex creation synchronizes multiple instances of
|
||||
the application that may have been started. */
|
||||
j = strlen(normalized_path);
|
||||
|
||||
b = CreateUniqueName();
|
||||
l = strlen(b);
|
||||
a = (char *)malloc(j + l + 50);
|
||||
memcpy(a, normalized_path, j);
|
||||
for (i = 0; i < j; i++) {
|
||||
/* backslashes are not allowed in mutex names */
|
||||
if (a[i] == '\\') a[i] = '/';
|
||||
}
|
||||
memcpy(a + j, b, l);
|
||||
memcpy(a + j + l, "GRacket-" GRACKET_GUID, strlen(GRACKET_GUID) + 9);
|
||||
mutex = CreateMutex(NULL, FALSE, a);
|
||||
alreadyrunning = (GetLastError() == ERROR_ALREADY_EXISTS ||
|
||||
GetLastError() == ERROR_ACCESS_DENIED);
|
||||
/* The call fails with ERROR_ACCESS_DENIED if the Mutex was
|
||||
created in a different users session because of passing
|
||||
NULL for the SECURITY_ATTRIBUTES on Mutex creation. */
|
||||
wm_is_gracket = RegisterWindowMessage(a);
|
||||
free(a);
|
||||
|
||||
if (alreadyrunning) {
|
||||
/* If another instance has been started, try to find it. */
|
||||
if (!EnumWindows((WNDENUMPROC)CheckWindow, (LPARAM)argv)) {
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
# include "../start/win_single.inc"
|
||||
|
||||
static void pre_filter_cmdline_arguments(int *argc, char ***argv)
|
||||
{
|
||||
|
|
|
@ -123,7 +123,7 @@ int IsFlag(LPCTSTR cmd, LPCTSTR flag)
|
|||
|
||||
#define ASSUME_ASCII_COMMAND_LINE
|
||||
#define GC_CAN_IGNORE
|
||||
#include "../racket/parse_cmdl.inc"
|
||||
#include "../start/parse_cmdl.inc"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
|
|
|
@ -272,8 +272,8 @@ DEF_CONFIG_DIR = -DINITIAL_CONFIG_DIRECTORY='"'"`cd $(srcdir)/../..; @PWD@`/etc"
|
|||
DEF_C_DIRS = $(DEF_COLLECTS_DIR) $(DEF_CONFIG_DIR)
|
||||
|
||||
MAIN_HEADER_DEPS = $(srcdir)/include/scheme.h $(srcdir)/include/schthread.h $(srcdir)/sconfig.h \
|
||||
$(srcdir)/src/stypes.h $(srcdir)/cmdline.inc $(srcdir)/parse_cmdl.inc \
|
||||
$(srcdir)/../start/config.inc $(srcdir)/../start/delayed.inc $(srcdir)/parse_cmdl.inc \
|
||||
$(srcdir)/src/stypes.h $(srcdir)/cmdline.inc $(srcdir)/../start/parse_cmdl.inc \
|
||||
$(srcdir)/../start/config.inc $(srcdir)/../start/delayed.inc \
|
||||
$(srcdir)/../start/embedded_dll.inc
|
||||
|
||||
main.@LTO@: $(srcdir)/main.c $(MAIN_HEADER_DEPS)
|
||||
|
|
|
@ -306,7 +306,7 @@ START_XFORM_SKIP;
|
|||
# endif
|
||||
|
||||
#if defined(__MINGW32__) || defined(WINMAIN_ALREADY)
|
||||
# include "parse_cmdl.inc"
|
||||
# include "../start/parse_cmdl.inc"
|
||||
#endif
|
||||
|
||||
#ifdef DOS_FILE_SYSTEM
|
||||
|
|
|
@ -86,6 +86,9 @@ static wchar_t *load_delayed_dll_x(HINSTANCE me, const char *lib, HMODULE *_load
|
|||
return t;
|
||||
}
|
||||
}
|
||||
|
||||
/* Should not get here */
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void load_delayed_dll(HINSTANCE me, const char *lib)
|
||||
|
|
|
@ -38,7 +38,7 @@ static void parse_embedded_dlls()
|
|||
{
|
||||
long rsrc_pos;
|
||||
|
||||
rsrc_pos = find_resource_offset(258);
|
||||
rsrc_pos = find_resource_offset(get_self_executable_path(), 258);
|
||||
if (rsrc_pos) {
|
||||
HANDLE fd = open_self();
|
||||
|
||||
|
|
169
racket/src/start/win_single.inc
Normal file
169
racket/src/start/win_single.inc
Normal file
|
@ -0,0 +1,169 @@
|
|||
/* ---------------------------------------- */
|
||||
/* single-instance detection */
|
||||
/* ---------------------------------------- */
|
||||
|
||||
static char *CreateUniqueName()
|
||||
{
|
||||
char desktop[MAX_PATH], session[32], *together;
|
||||
int dlen, slen;
|
||||
|
||||
{
|
||||
// Name should be desktop unique, so add current desktop name
|
||||
HDESK hDesk;
|
||||
ULONG cchDesk = MAX_PATH - 1;
|
||||
|
||||
hDesk = GetThreadDesktop(GetCurrentThreadId());
|
||||
|
||||
if (!GetUserObjectInformation( hDesk, UOI_NAME, desktop, cchDesk, &cchDesk))
|
||||
desktop[0] = 0;
|
||||
else
|
||||
desktop[MAX_PATH - 1] = 0;
|
||||
}
|
||||
|
||||
{
|
||||
// Name should be session unique, so add current session id
|
||||
HANDLE hToken = NULL;
|
||||
// Try to open the token (fails on Win9x) and check necessary buffer size
|
||||
if (OpenProcessToken(GetCurrentProcess(), TOKEN_QUERY, &hToken)) {
|
||||
DWORD cbBytes = 0;
|
||||
|
||||
if(!GetTokenInformation( hToken, TokenStatistics, NULL, cbBytes, &cbBytes )
|
||||
&& GetLastError() == ERROR_INSUFFICIENT_BUFFER) {
|
||||
PTOKEN_STATISTICS pTS;
|
||||
|
||||
pTS = (PTOKEN_STATISTICS)malloc(cbBytes);
|
||||
|
||||
if(GetTokenInformation(hToken, TokenStatistics, (LPVOID)pTS, cbBytes, &cbBytes)) {
|
||||
sprintf(session, "-%08x%08x-",
|
||||
pTS->AuthenticationId.HighPart,
|
||||
pTS->AuthenticationId.LowPart);
|
||||
} else
|
||||
session[0] = 0;
|
||||
free(pTS);
|
||||
} else {
|
||||
session[0] = 0;
|
||||
}
|
||||
} else
|
||||
session[0] = 0;
|
||||
}
|
||||
|
||||
dlen = strlen(desktop);
|
||||
slen = strlen(session);
|
||||
together = (char *)malloc(slen + dlen + 1);
|
||||
memcpy(together, desktop, dlen);
|
||||
memcpy(together + dlen, session, slen);
|
||||
together[dlen + slen] = 0;
|
||||
|
||||
return together;
|
||||
}
|
||||
|
||||
#define GRACKET_GUID "B2261834-D535-44dd-8511-A26FC8F97DD0"
|
||||
|
||||
static int wm_is_gracket;
|
||||
|
||||
static BOOL CALLBACK CheckWindow(HWND wnd, LPARAM param)
|
||||
{
|
||||
int i, len, gl;
|
||||
DWORD w;
|
||||
char **argv, *v;
|
||||
COPYDATASTRUCT cd;
|
||||
DWORD_PTR result;
|
||||
LRESULT ok;
|
||||
|
||||
ok = SendMessageTimeout(wnd, wm_is_gracket,
|
||||
0, 0,
|
||||
SMTO_BLOCK |
|
||||
SMTO_ABORTIFHUNG,
|
||||
200,
|
||||
&result);
|
||||
|
||||
printf("try %p result %d\n", wnd, result);
|
||||
|
||||
if (ok == 0)
|
||||
return TRUE; /* ignore and continue */
|
||||
if ((intptr_t)result == 79) {
|
||||
/* found it */
|
||||
} else
|
||||
return TRUE; /* continue search */
|
||||
|
||||
/* wnd is owned by another instance of this application */
|
||||
|
||||
SetForegroundWindow(wnd);
|
||||
if (IsIconic(wnd))
|
||||
ShowWindow(wnd, SW_RESTORE);
|
||||
|
||||
argv = (char **)param;
|
||||
|
||||
len = gl = strlen(GRACKET_GUID);
|
||||
len += 4 + sizeof(DWORD);
|
||||
for (i = 1; argv[i]; i++) {
|
||||
len += sizeof(DWORD) + strlen(argv[i]);
|
||||
}
|
||||
w = i - 1;
|
||||
|
||||
v = (char *)malloc(len);
|
||||
memcpy(v, GRACKET_GUID, gl);
|
||||
memcpy(v + gl, "OPEN", 4);
|
||||
memcpy(v + gl + 4, &w, sizeof(DWORD));
|
||||
len = gl + 4 + sizeof(DWORD);
|
||||
for (i = 1; argv[i]; i++) {
|
||||
w = strlen(argv[i]);
|
||||
memcpy(v + len, &w, sizeof(DWORD));
|
||||
len += sizeof(DWORD);
|
||||
memcpy(v + len, argv[i], w);
|
||||
len += w;
|
||||
}
|
||||
|
||||
cd.dwData = 79;
|
||||
cd.cbData = len;
|
||||
cd.lpData = v;
|
||||
|
||||
SendMessage(wnd, WM_COPYDATA, (WPARAM)wnd, (LPARAM)&cd);
|
||||
|
||||
free(v);
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
static int CheckSingleInstance(char *normalized_path, char **argv)
|
||||
{
|
||||
/* Check for an existing instance: */
|
||||
if (check_for_another[0] != 'n') {
|
||||
int alreadyrunning;
|
||||
HANDLE mutex;
|
||||
int j, l, i;
|
||||
char *a, *b;
|
||||
|
||||
/* This mutex creation synchronizes multiple instances of
|
||||
the application that may have been started. */
|
||||
j = strlen(normalized_path);
|
||||
|
||||
b = CreateUniqueName();
|
||||
l = strlen(b);
|
||||
a = (char *)malloc(j + l + 50);
|
||||
memcpy(a, normalized_path, j);
|
||||
for (i = 0; i < j; i++) {
|
||||
/* backslashes are not allowed in mutex names */
|
||||
if (a[i] == '\\') a[i] = '/';
|
||||
}
|
||||
memcpy(a + j, b, l);
|
||||
memcpy(a + j + l, "GRacket-" GRACKET_GUID, strlen(GRACKET_GUID) + 9);
|
||||
mutex = CreateMutex(NULL, FALSE, a);
|
||||
alreadyrunning = (GetLastError() == ERROR_ALREADY_EXISTS ||
|
||||
GetLastError() == ERROR_ACCESS_DENIED);
|
||||
/* The call fails with ERROR_ACCESS_DENIED if the Mutex was
|
||||
created in a different users session because of passing
|
||||
NULL for the SECURITY_ATTRIBUTES on Mutex creation. */
|
||||
wm_is_gracket = RegisterWindowMessage(a);
|
||||
free(a);
|
||||
|
||||
if (alreadyrunning) {
|
||||
/* If another instance has been started, try to find it. */
|
||||
if (!EnumWindows((WNDENUMPROC)CheckWindow, (LPARAM)argv)) {
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
|
@ -14,6 +14,11 @@ DEST = ..\..\build\raw_racketcs.exe
|
|||
GDEST = ..\..\build\raw_gracketcs.exe
|
||||
CSDIR = ..\..\cs\c
|
||||
|
||||
MAIN_DEPS = ..\..\start\config.inc \
|
||||
..\..\start\parse_cmdl.inc \
|
||||
..\..\start\delayed.inc \
|
||||
..\..\start\win_single.inc
|
||||
|
||||
FLAGS = /DWIN32
|
||||
COMP_SUBDIR = /DCS_COMPILED_SUBDIR=1
|
||||
|
||||
|
@ -25,14 +30,14 @@ $(DEST_DLL): $(CSDIR)\boot.c libracket.res $(RKTIO_LIB)
|
|||
libracket.res: libracket.rc
|
||||
rc /l 0x409 /folibracket.res libracket.rc
|
||||
|
||||
$(DEST): $(CSDIR)\main.c $(DEST_DLL) racket.res
|
||||
$(DEST): $(CSDIR)\main.c $(MAIN_DEPS) $(DEST_DLL) racket.res
|
||||
cl /Fe$(DEST) /Ox /MT $(COMP_SUBDIR) $(FLAGS) $(INCS) $(CSDIR)\main.c racket.res $(WIN32_LIBS)
|
||||
|
||||
racket.res: ../racket/racket.rc ../racket/racket.ico
|
||||
rc /l 0x409 /foracket.res ../racket/racket.rc
|
||||
|
||||
$(GDEST): $(CSDIR)\grmain.c $(DEST_DLL) gracket.res
|
||||
cl /Fe$(GDEST) /Ox /MT $(COMP_SUBDIR) $(FLAGS) $(INCS) $(CSDIR)\grmain.c gracket.res $(WIN32_LIBS) /subsystem:windows
|
||||
$(GDEST): $(CSDIR)\grmain.c $(CSDIR)\main.c $(MAIN_DEPS) $(DEST_DLL) gracket.res
|
||||
cl /Fe$(GDEST) /Ox /MT $(COMP_SUBDIR) $(FLAGS) $(INCS) $(CSDIR)\grmain.c gracket.res $(WIN32_LIBS)
|
||||
|
||||
gracket.res: ../gracket/gracket.rc ../gracket/gracket.ico
|
||||
rc /l 0x409 /fogracket.res ../gracket/gracket.rc
|
||||
|
|
|
@ -11,6 +11,7 @@
|
|||
|
||||
(define scheme-dir-provided? #f)
|
||||
(define abs-scheme-dir (build-path here 'up "build" "ChezScheme"))
|
||||
(define pull? #f)
|
||||
(define machine (if (= 32 (system-type 'word))
|
||||
"ti3nt"
|
||||
"ta6nt"))
|
||||
|
@ -25,6 +26,8 @@
|
|||
(unless (equal? dir "")
|
||||
(set! scheme-dir-provided? #t)
|
||||
(set! abs-scheme-dir (path->complete-path dir)))]
|
||||
[("--pull") "Use `git pull` on auto-cloned Chez Scheme repo"
|
||||
(set! pull? #t)]
|
||||
[("--racketcs-suffix") str "Select the suffix for RacketCS"
|
||||
(set! cs-suffix (string-upcase str))]
|
||||
[("--boot-mode") mode "Select the mode for Racket bootstrapping"
|
||||
|
@ -87,9 +90,10 @@
|
|||
scheme-dir
|
||||
git-clone-args)]))
|
||||
|
||||
(unless scheme-dir-provided?
|
||||
(parameterize ([current-directory scheme-dir])
|
||||
(system*! "git" "pull")))
|
||||
(when pull?
|
||||
(unless scheme-dir-provided?
|
||||
(parameterize ([current-directory scheme-dir])
|
||||
(system*! "git" "pull"))))
|
||||
|
||||
(unless (file-exists? (build-path scheme-dir "zlib" "Makefile"))
|
||||
(parameterize ([current-directory scheme-dir])
|
||||
|
|
Loading…
Reference in New Issue
Block a user