1
0
mirror of https://github.com/gryf/wmaker.git synced 2025-12-19 20:38:08 +01:00

- Removed legacy OFFIX_DND support code

- Fixed the signal handler for crashes (ie, removed it) and made wmaker
  restarting be made automatically by a monitoring process.
- Made NetWM support be enabled by default
- Removed old code to store/restore workspace state (now relies on netwm)
This commit is contained in:
kojima
2004-10-13 05:09:08 +00:00
parent 6830b05716
commit 879b00a57b
22 changed files with 273 additions and 339 deletions

View File

@@ -152,7 +152,11 @@ Changes since version 0.80.2:
has. (This also is to fix problems with KDE 3.3.0 apps, but not only them).
- Fixed bug with autostart and exit scripts not being executed if user
GNUstep path was different from ~/GNUstep (when setting GNUSTEP_USER_ROOT)
- Removed legacy OFFIX_DND support code
- Fixed the signal handler for crashes (ie, removed it) and made wmaker
restarting be made automatically by a monitoring process.
- Made NetWM support be enabled by default
- Removed old code to store/restore workspace state (now relies on netwm)
Changes since version 0.80.1:
.............................

View File

@@ -412,14 +412,6 @@ AC_ARG_ENABLE(openlook,
fi])
AC_ARG_ENABLE(netwm,
[ --enable-netwm enable support for FreeDesktop hints ],
[if test x$enableval = xyes; then
AC_DEFINE(NETWM_HINTS, 1, [define if you want NETWM hints support])
netwm_on=yes
fi])
AC_ARG_ENABLE(vdesktop,
[ --enable-vdesktop enable virtual desktop],
[if test x$enableval = xyes; then
@@ -1137,15 +1129,11 @@ if test "$openlook_on" = "yes"; then
extrasupport="OpenLook $extrasupport"
fi
if test "$gnome_on" = "yes"; then
extrasupport="Gnome $extrasupport"
extrasupport="Gnome-1.x $extrasupport"
fi
if test "$kde_on" = "yes"; then
extrasupport="KDE $extrasupport"
extrasupport="KDE-1.x $extrasupport"
fi
if test "$netwm_on" = "yes"; then
extrasupport="NetWM $extrasupport"
fi
if test "x$extrasupport" = "x"; then
extrasupport="None"
fi
@@ -1162,7 +1150,7 @@ echo "Use inline MMX(tm) x86 assembly : $mmx_support"
echo "Antialiased text support in WINGs : $xft"
echo "Xinerama extension support : $xinerama"
echo "Virtual desktop support : $vdesktop_on"
echo "Additionally supported environments : $extrasupport"
echo "Supported legacy environments : $extrasupport"
echo "Translated message files to install : $mof"
dnl echo "Supported languages beside English : $languages"
if test "x$MOFILES" != "x"; then

View File

@@ -50,6 +50,7 @@ wmaker_SOURCES = \
menu.c \
menu.h \
misc.c \
monitor.c \
motif.c \
motif.h \
moveres.c \

View File

@@ -481,6 +481,7 @@ typedef struct WPreferences {
unsigned int norestore:1; /* don't restore session */
unsigned int create_stdcmap:1; /* create std colormap */
unsigned int nopolling:1; /* don't poll for defaults changes */
unsigned int restarting:2;
} flags; /* internal flags */
} WPreferences;

View File

@@ -193,7 +193,7 @@ wAppIconDestroy(WAppIcon *aicon)
wIconDestroy(aicon->icon);
if (aicon->command)
wfree(aicon->command);
#ifdef OFFIX_DND
#ifdef XDND
if (aicon->dnd_command)
wfree(aicon->dnd_command);
#endif

View File

@@ -45,7 +45,7 @@ typedef struct WAppIcon {
char *command; /* command used to launch app */
#ifdef OFFIX_DND
#ifdef XDND
char *dnd_command; /* command to use when something is */
/* dropped on us */
#endif

View File

@@ -81,10 +81,6 @@ extern WPreferences wPreferences;
extern XContext wWinContext;
#ifdef OFFIX_DND
extern Atom _XA_DND_PROTOCOL;
#endif
#define MOD_MASK wPreferences.modifier_mask
@@ -97,7 +93,7 @@ extern void appIconMouseDown(WObjDescriptor *desc, XEvent *event);
static WMPropList *dCommand=NULL;
static WMPropList *dPasteCommand=NULL;
#ifdef OFFIX_DND
#ifdef XDND /* XXX was OFFIX */
static WMPropList *dDropCommand=NULL;
#endif
static WMPropList *dAutoLaunch, *dLock;
@@ -142,22 +138,6 @@ static void clipAutoRaise(void *cdata);
static void showClipBalloon(WDock *dock, int workspace);
#ifdef OFFIX_DND
#define DndNotDnd -1
#define DndUnknown 0
#define DndRawData 1
#define DndFile 2
#define DndFiles 3
#define DndText 4
#define DndDir 5
#define DndLink 6
#define DndExe 7
#define DndEND 8
#endif /* OFFIX_DND */
static void
@@ -168,7 +148,9 @@ make_keys()
dCommand = WMRetainPropList(WMCreatePLString("Command"));
dPasteCommand = WMRetainPropList(WMCreatePLString("PasteCommand"));
#ifdef XDND
dDropCommand = WMRetainPropList(WMCreatePLString("DropCommand"));
#endif
dLock = WMRetainPropList(WMCreatePLString("Lock"));
dAutoLaunch = WMRetainPropList(WMCreatePLString("AutoLaunch"));
dName = WMRetainPropList(WMCreatePLString("Name"));
@@ -1402,13 +1384,13 @@ make_icon_state(WAppIcon *btn)
(btn->xindex != 0 || btn->yindex != 0))
WMPutInPLDictionary(node, dOmnipresent, omnipresent);
#ifdef OFFIX_DND
#ifdef XDND /* was OFFIX */
if (btn->dnd_command) {
command = WMCreatePLString(btn->dnd_command);
WMPutInPLDictionary(node, dDropCommand, command);
WMReleasePropList(command);
}
#endif /* OFFIX_DND */
#endif /* XDND */
if (btn->paste_command) {
command = WMCreatePLString(btn->paste_command);
@@ -1625,7 +1607,7 @@ restore_icon_state(WScreen *scr, WMPropList *info, int type, int index)
aicon->icon->core->descriptor.parent = aicon;
#ifdef OFFIX_DND
#ifdef XDND /* was OFFIX */
cmd = WMGetFromPLDictionary(info, dDropCommand);
if (cmd)
aicon->dnd_command = wstrdup(WMGetFromPLString(cmd));
@@ -1732,7 +1714,7 @@ wClipRestoreState(WScreen *scr, WMPropList *clip_state)
}
}
#ifdef OFFIX_DND
#ifdef XDND /* was OFFIX */
value = WMGetFromPLDictionary(clip_state, dDropCommand);
if (value && WMIsPLString(value))
icon->dnd_command = wstrdup(WMGetFromPLString(value));
@@ -2042,7 +2024,7 @@ wDockDoAutoLaunch(WDock *dock, int workspace)
}
#ifdef OFFIX_DND
#ifdef XDND /* was OFFIX */
static WDock*
findDock(WScreen *scr, XEvent *event, int *icon_pos)
{
@@ -2130,7 +2112,7 @@ wDockReceiveDNDDrop(WScreen *scr, XEvent *event)
}
return False;
}
#endif /* OFFIX_DND */
#endif /* XDND */
@@ -2225,7 +2207,7 @@ wDockAttachIcon(WDock *dock, WAppIcon *icon, int x, int y)
if (wPreferences.auto_arrange_icons)
wArrangeIcons(dock->screen_ptr, True);
#ifdef OFFIX_DND
#ifdef XDND /* was OFFIX */
if (icon->command && !icon->dnd_command) {
int len = strlen(icon->command)+8;
icon->dnd_command = wmalloc(len);
@@ -2407,7 +2389,7 @@ wDockDetach(WDock *dock, WAppIcon *icon)
wfree(icon->command);
icon->command = NULL;
}
#ifdef OFFIX_DND
#ifdef XDND /* was OFFIX */
if (icon->dnd_command) {
wfree(icon->dnd_command);
icon->dnd_command = NULL;
@@ -3337,9 +3319,12 @@ trackDeadProcess(pid_t pid, unsigned char status, WDock *dock)
char msg[PATH_MAX];
char *cmd;
#ifdef XDND
if (icon->drop_launch)
cmd = icon->dnd_command;
else if (icon->paste_launch)
else
#endif
if (icon->paste_launch)
cmd = icon->paste_command;
else
cmd = icon->command;

View File

@@ -92,7 +92,7 @@ WAppIcon *wDockFindIconForWindow(WDock *dock, Window window);
void wDockDoAutoLaunch(WDock *dock, int workspace);
void wDockLaunchWithState(WDock *dock, WAppIcon *btn, WSavedState *state);
#ifdef OFFIX_DND
#ifdef XDND
int wDockReceiveDNDDrop(WScreen *scr, XEvent *event);
#endif

View File

@@ -119,7 +119,7 @@ updatePasteCommand(WAppIcon *icon, char *command)
#ifdef OFFIX_DND
#ifdef XDND
static void
updateDNDCommand(WAppIcon *icon, char *command)
{
@@ -131,7 +131,7 @@ updateDNDCommand(WAppIcon *icon, char *command)
}
icon->dnd_command = command;
}
#endif /* OFFIX_DND */
#endif /* XDND */
static void
@@ -258,7 +258,7 @@ panelBtnCallback(WMWidget *self, void *data)
text = NULL;
}
updateCommand(panel->editedIcon, text);
#ifdef OFFIX_DND
#ifdef XDND
/* cannot free text from this, because it will be not be duplicated
* in updateDNDCommand */
text = WMGetTextFieldText(panel->dndCommandField);
@@ -385,7 +385,7 @@ ShowDockAppSettingsPanel(WAppIcon *aicon)
panel->dndCommandLabel = WMCreateLabel(panel->dndCommandFrame);
WMResizeWidget(panel->dndCommandLabel, 256, 18);
WMMoveWidget(panel->dndCommandLabel, 10, 45);
#ifdef OFFIX_DND
#ifdef XDND
WMSetTextFieldText(panel->dndCommandField, aicon->dnd_command);
WMSetLabelText(panel->dndCommandLabel,
_("%d will be replaced with the file name"));

View File

@@ -95,10 +95,6 @@ extern Atom _XA_GNUSTEP_TITLEBAR_STATE;
extern Atom _XA_WINDOWMAKER_WM_FUNCTION;
extern Atom _XA_WINDOWMAKER_COMMAND;
#ifdef OFFIX_DND
extern Atom _XA_DND_PROTOCOL;
#endif
#ifdef SHAPE
extern Bool wShapeSupported;
@@ -1017,16 +1013,7 @@ handleClientMessage(XEvent *event)
} else if (wXDNDProcessClientMessage(&event->xclient)) {
/* do nothing */
#endif /* XDND */
#ifdef OFFIX_DND
} else if (event->xclient.message_type==_XA_DND_PROTOCOL) {
WScreen *scr = wScreenForWindow(event->xclient.window);
if (scr && wDockReceiveDNDDrop(scr,event))
goto redirect_message;
#endif /* OFFIX_DND */
} else {
#ifdef OFFIX_DND
redirect_message:
#endif
/*
* Non-standard thing, but needed by OffiX DND.
* For when the icon frame gets a ClientMessage

View File

@@ -1076,7 +1076,7 @@ wFrameWindowPaint(WFrameWindow *fwin)
break;
}
y = *fwin->title_clearance + TITLEBAR_EXTEND_SPACE;
y = *fwin->title_clearance + TITLEBAR_EXTEND_SPACE - 1;
h = WMFontHeight(*fwin->font);
/* We use a w+2 buffer to have an extra pixel on the left and

View File

@@ -115,11 +115,6 @@ Atom _XA_WINDOWMAKER_ICON_SIZE;
Atom _XA_WINDOWMAKER_ICON_TILE;
#ifdef OFFIX_DND
Atom _XA_DND_PROTOCOL;
Atom _XA_DND_SELECTION;
#endif
/* cursors */
Cursor wCursor[WCUR_LAST];
@@ -148,7 +143,6 @@ char WDelayedActionSet = 0;
int wVisualID = -1;
/* notifications */
const char *WMNManaged = "WMNManaged";
const char *WMNUnmanaged = "WMNUnmanaged";
@@ -175,6 +169,7 @@ static int ArgCount;
extern void EventLoop();
extern void StartUp();
extern int MonitorLoop(int argc, char **argv);
static Bool multiHead = True;
@@ -182,6 +177,8 @@ static Bool multiHead = True;
static int LogStdIn = -1, LogStdOut = -1, LogStdErr = -1;
static int real_main(int argc, char **argv);
void
Exit(int status)
{
@@ -226,7 +223,7 @@ Restart(char *manager, Bool abortOnFailure)
wsyserror(_("could not exec %s"), prog);
}
if (abortOnFailure)
exit(-1);
exit(7);
}
@@ -583,8 +580,32 @@ getFullPath(char *path)
}
#endif
int
main(int argc, char **argv)
{
int i;
int i_am_the_monitor= 1;
for (i= 1; i < argc; i++)
{
if (strncmp(argv[i], "--for-real", strlen("--for-real"))==0)
{
i_am_the_monitor= 0;
break;
}
}
if (i_am_the_monitor)
return MonitorLoop(argc, argv);
else
return real_main(argc, argv);
}
static int
real_main(int argc, char **argv)
{
int i, restart=0;
char *str, *alt;
@@ -601,8 +622,13 @@ main(int argc, char **argv)
str = wstrconcat("WMAKER_BIN_NAME=", argv[0]);
putenv(str);
ArgCount = argc;
Arguments = argv;
ArgCount = argc+1;
Arguments = wmalloc(sizeof(char*)*(ArgCount+2));
for (i= 0; i < argc; i++)
Arguments[i]= argv[i];
/* add the extra option to signal that we're just restarting wmaker */
Arguments[argc]= "--for-real=";
Arguments[argc+1]= NULL;
WMInitializeApplication("WindowMaker", &argc, argv);
@@ -638,7 +664,13 @@ main(int argc, char **argv)
wPreferences.flags.nocpp=1;
} else
#endif
if (strcmp(argv[i], "-no-autolaunch")==0
if (strcmp(argv[i], "--for-real")==0) {
wPreferences.flags.restarting = 0;
} else if (strcmp(argv[i], "--for-real=")==0) {
wPreferences.flags.restarting = 1;
} else if (strcmp(argv[i], "--for-real-")==0) {
wPreferences.flags.restarting = 2;
} else if (strcmp(argv[i], "-no-autolaunch")==0
|| strcmp(argv[i], "--no-autolaunch")==0) {
wPreferences.flags.noautolaunch = 1;
} else if (strcmp(argv[i], "-dont-restore")==0

View File

@@ -67,6 +67,12 @@ extern WPreferences wPreferences;
/***** Local Stuff ******/
#define WSS_ROOTMENU (1<<0)
#define WSS_SWITCHMENU (1<<1)
#define WSS_WSMENU (1<<2)
static struct {
int steps;
int delay;

View File

@@ -56,10 +56,6 @@ extern WPreferences wPreferences;
extern Time LastTimestamp;
#ifdef OFFIX_DND
extern Atom _XA_DND_SELECTION;
#endif
#ifdef USECPP
static void
@@ -705,44 +701,6 @@ getuserinput(WScreen *scr, char *line, int *ptr)
}
#ifdef OFFIX_DND
static char*
get_dnd_selection(WScreen *scr)
{
XTextProperty text_ret;
int result;
char **list;
char *flat_string;
int count;
result=XGetTextProperty(dpy, scr->root_win, &text_ret, _XA_DND_SELECTION);
if (result==0 || text_ret.value==NULL || text_ret.encoding==None
|| text_ret.format==0 || text_ret.nitems == 0) {
wwarning(_("unable to get dropped data from DND drop"));
return NULL;
}
XTextPropertyToStringList(&text_ret, &list, &count);
if (!list || count<1) {
XFree(text_ret.value);
wwarning(_("error getting dropped data from DND drop"));
return NULL;
}
flat_string = wtokenjoin(list, count);
if (!flat_string) {
wwarning(_("out of memory while getting data from DND drop"));
}
XFreeStringList(list);
XFree(text_ret.value);
return flat_string;
}
#endif /* OFFIX_DND */
#define S_NORMAL 0
#define S_ESCAPE 1
#define S_OPTION 2
@@ -768,7 +726,7 @@ ExpandOptions(WScreen *scr, char *cmdline)
char *out, *nout;
char *selection=NULL;
char *user_input=NULL;
#if defined(OFFIX_DND) || defined(XDND)
#ifdef XDND
char *dropped_thing=NULL;
#endif
char tmpbuf[TMPBUFSIZE];
@@ -879,13 +837,11 @@ ExpandOptions(WScreen *scr, char *cmdline)
}
break;
#if defined(OFFIX_DND) || defined(XDND)
case 'd':
#ifdef XDND
case 'd':
if(scr->xdestring) {
dropped_thing = wstrdup(scr->xdestring);
}
#endif
if (!dropped_thing) {
dropped_thing = get_dnd_selection(scr);
}
@@ -904,7 +860,7 @@ ExpandOptions(WScreen *scr, char *cmdline)
strcat(out,dropped_thing);
optr+=slen;
break;
#endif /* OFFIX_DND */
#endif /* XDND */
case 's':
if (!selection) {
@@ -1262,41 +1218,6 @@ StrConcatDot(char *a, char *b)
}
#ifndef NETWM_HINTS
static Atom net_wm_pid = None;
int
GetPidForWindow(Window win)
{
Atom type_ret;
int fmt_ret;
unsigned long nitems_ret;
unsigned long bytes_after_ret;
long *data = 0;
int pid;
if (net_wm_pid == None) {
net_wm_pid = XInternAtom(dpy, "_NET_WM_PID", False);
}
if (XGetWindowProperty(dpy, win, net_wm_pid, 0, 1, False,
XA_CARDINAL, &type_ret, &fmt_ret, &nitems_ret,
&bytes_after_ret,
(unsigned char**)&data)==Success && data) {
pid = *data;
XFree(data);
} else {
pid = 0;
}
return pid;
}
#endif
Bool
GetCommandForPid(int pid, char ***argv, int *argc)
{

152
src/monitor.c Normal file
View File

@@ -0,0 +1,152 @@
/* monitor.c - monitors the wmaker process
*
* Window Maker window manager
*
* Copyright (c) 1997-2004 Alfredo K. Kojima
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
* USA.
*/
#include "wconfig.h"
#include <unistd.h>
#include <stdlib.h>
#include <time.h>
#include <signal.h>
#include <sys/wait.h>
#ifdef __FreeBSD__
#include <sys/signal.h>
#endif
#include <X11/Xlib.h>
#include <X11/Xutil.h>
#include <X11/Xproto.h>
#include "WindowMaker.h"
#include "screen.h"
#include "window.h"
#include "dialog.h"
#include "funcs.h"
/****** Global Variables ******/
extern WPreferences wPreferences;
extern int wScreenCount;
int showCrashDialog(int sig)
{
int crashAction;
Display *dpy;
dpy = XOpenDisplay("");
if (dpy) {
/* XXX TODO make sure that window states are saved and restored via netwm */
XGrabServer(dpy);
crashAction = wShowCrashingDialogPanel(sig);
XCloseDisplay(dpy);
dpy = NULL;
} else {
wsyserror(_("cannot open connection for crashing dialog panel. Aborting."));
crashAction = WMAbort;
}
if (crashAction == WMRestart)
{
int i;
wmessage(_("trying to start alternate window manager..."));
for (i=0; i<WMGetArrayItemCount(wPreferences.fallbackWMs); i++) {
Restart(WMGetFromArray(wPreferences.fallbackWMs, i), False);
}
wfatal(_("failed to start alternate window manager. Aborting."));
return 0;
}
else if (crashAction == WMAbort)
return 0;
else
return 1;
}
int MonitorLoop(int argc, char **argv)
{
pid_t pid;
char **child_argv= wmalloc(sizeof(char*)*(argc+2));
int i, status;
time_t last_start;
for (i= 0; i < argc; i++)
child_argv[i]= argv[i];
child_argv[i++]= "--for-real";
child_argv[i]= NULL;
for (;;)
{
last_start= time(NULL);
/* Start Window Maker */
pid= fork();
if (pid == 0)
{
execvp(child_argv[0], child_argv);
wsyserror(_("Error respawning Window Maker"));
exit(1);
}
else if (pid < 0)
{
wsyserror(_("Error respawning Window Maker"));
exit(1);
}
if (waitpid(pid, &status, 0) < 0)
{
wsyserror(_("Error during monitoring of Window Maker process."));
break;
}
child_argv[argc]= "--for-real-";
/* Check if the wmaker process exited due to a crash */
if (WIFSIGNALED(status) &&
(WTERMSIG(status) == SIGSEGV ||
WTERMSIG(status) == SIGBUS ||
WTERMSIG(status) == SIGILL ||
WTERMSIG(status) == SIGFPE))
{
/* If so, we check when was the last restart.
* If it was less than 5s ago, it's a bad sign, so we show
* the crash panel and ask the user what to do */
if (time(NULL) - last_start < 5)
{
if (showCrashDialog(WTERMSIG(status)) == 0)
return 1;
}
wwarning(_("Window Maker exited due to a crash (signal %i) and will be restarted."),
WTERMSIG(status));
}
else
break;
}
return 0;
}

View File

@@ -1204,14 +1204,6 @@ wScreenSaveState(WScreen *scr)
make_keys();
/* Save current workspace, so can go back to it upon restart. */
data[0] = scr->current_workspace;
data[1] = WFLAGS_NONE;
XChangeProperty(dpy, scr->root_win, _XA_WINDOWMAKER_STATE,
_XA_WINDOWMAKER_STATE, 32, PropModeReplace,
(unsigned char *) data, 2);
/* save state of windows */
wwin = scr->focused_window;
while (wwin) {

View File

@@ -335,16 +335,6 @@ typedef struct _WScreen {
} WScreen;
#define WSS_ROOTMENU (1<<0)
#define WSS_SWITCHMENU (1<<1)
#define WSS_WSMENU (1<<2)
/* changes must update wSaveScreenState/getWorkspaceState */
typedef struct WWorkspaceState {
int flags;
int workspace;
} WWorkspaceState;
WScreen *wScreenInit(int screen_number);
void wScreenSaveState(WScreen *scr);

View File

@@ -138,11 +138,6 @@ extern Atom _XA_WINDOWMAKER_ICON_TILE;
extern Atom _XA_GNUSTEP_WM_MINIATURIZE_WINDOW;
extern Atom _XA_GNUSTEP_TITLEBAR_STATE;
#ifdef OFFIX_DND
extern Atom _XA_DND_PROTOCOL;
extern Atom _XA_DND_SELECTION;
#endif
/* cursors */
extern Cursor wCursor[WCUR_LAST];
@@ -311,25 +306,10 @@ dummyHandler(int sig)
static RETSIGTYPE
handleSig(int sig)
{
static int already_crashed = 0;
int dumpcore = 0;
#ifndef NO_EMERGENCY_AUTORESTART
int crashAction, i;
char *argv[2];
argv[1] = NULL;
#endif
/*
* No functions that potentially do Xlib calls should be called from
* here. Xlib calls are not reentrant so the integrity of Xlib is
* not guaranteed if a Xlib call is made from a signal handler.
*/
#ifdef SYS_SIGLIST_DECLARED
wfatal(_("got signal %i (%s)\n"), sig, sys_siglist[sig]);
wfatal("got signal %i (%s)\n", sig, sys_siglist[sig]);
#else
wfatal(_("got signal %i\n"), sig);
wfatal("got signal %i\n", sig);
#endif
/* Setting the signal behaviour back to default and then reraising the
@@ -339,95 +319,12 @@ handleSig(int sig)
*/
if (sig==SIGSEGV || sig==SIGFPE || sig==SIGBUS || sig==SIGILL
|| sig==SIGABRT) {
if (already_crashed) {
wfatal(_("crashed while trying to do some post-crash cleanup. Aborting immediatelly."));
signal(sig, SIG_DFL);
kill(getpid(), sig);
return;
}
already_crashed = 1;
dumpcore = 1;
/*
* Yeah, we shouldn't do this, but it's already crashed anyway :P
*/
#ifndef NO_EMERGENCY_AUTORESTART
/* Close the X connection and open a new one. This is to avoid messing
* Xlib because we call to Xlib functions in a signal handler.
*/
if (dpy)
XCloseDisplay(dpy);
dpy = XOpenDisplay("");
if (dpy) {
CARD32 data[2];
WWindow *wwin;
XGrabServer(dpy);
crashAction = wShowCrashingDialogPanel(sig);
/*
* Save current workspace, so can go back to it if restarting.
* Also add hint that we crashed, so that windows will be placed
* correctly upon restart.
*/
for (i=0; i<wScreenCount; i++) {
data[0] = wScreen[i]->current_workspace; /* workspace number */
data[1] = WFLAGS_CRASHED; /* signal that we crashed */
XChangeProperty(dpy, wScreen[i]->root_win,
_XA_WINDOWMAKER_STATE, _XA_WINDOWMAKER_STATE,
32, PropModeReplace, (unsigned char*) data, 2);
/* save state of windows */
wwin = wScreen[i]->focused_window;
while (wwin) {
wWindowSaveState(wwin);
wwin = wwin->prev;
}
}
XCloseDisplay(dpy);
dpy = NULL;
} else {
wsyserror(_("cannot open connection for crashing dialog panel. Aborting."));
crashAction = WMAbort;
}
if (crashAction == WMAbort) {
signal(sig, SIG_DFL);
kill(getpid(), sig);
return;
}
if (crashAction == WMRestart) {
/* we try to restart Window Maker */
wmessage(_("trying to restart Window Maker..."));
Restart(NULL, False);
/* fallback to alternate window manager then */
}
wmessage(_("trying to start alternate window manager..."));
for (i=0; i<WMGetArrayItemCount(wPreferences.fallbackWMs); i++) {
Restart(WMGetFromArray(wPreferences.fallbackWMs, i), False);
}
wfatal(_("failed to start alternate window manager. Aborting."));
#else
wfatal(_("a fatal error has occured, probably due to a bug. "
"Please fill the included BUGFORM and report it."));
#endif /* !NO_EMERGENCY_AUTORESTART */
signal(sig, SIG_DFL);
kill(getpid(), sig);
return;
}
wAbort(dumpcore);
wAbort(0);
}
@@ -462,34 +359,6 @@ buryChild(int foo)
}
static int
getWorkspaceState(Window root, WWorkspaceState **state)
{
Atom type_ret;
int fmt_ret;
unsigned long nitems_ret;
unsigned long bytes_after_ret;
CARD32 *data;
if (XGetWindowProperty(dpy, root, _XA_WINDOWMAKER_STATE, 0, 2,
True, _XA_WINDOWMAKER_STATE,
&type_ret, &fmt_ret, &nitems_ret, &bytes_after_ret,
(unsigned char **)&data)!=Success || !data)
return 0;
*state = wmalloc(sizeof(WWorkspaceState));
(*state)->workspace = data[0];
(*state)->flags = data[1];
XFree(data);
if (*state && type_ret==_XA_WINDOWMAKER_STATE)
return 1;
else
return 0;
}
static void
getOffendingModifiers()
{
@@ -735,7 +604,6 @@ static char *atomNames[] = {
void
StartUp(Bool defaultScreenOnly)
{
WWorkspaceState *ws_state;
struct sigaction sig_action;
int j, max;
Atom atom[sizeof(atomNames)/sizeof(char*)];
@@ -797,10 +665,6 @@ StartUp(Bool defaultScreenOnly)
_XA_GNUSTEP_WM_MINIATURIZE_WINDOW = atom[18];
_XA_GNUSTEP_TITLEBAR_STATE = atom[19];
#ifdef OFFIX_DND
_XA_DND_SELECTION = XInternAtom(dpy, "DndSelection", False);
_XA_DND_PROTOCOL = XInternAtom(dpy, "DndProtocol", False);
#endif
#ifdef XDND
wXDNDInitializeAtoms();
#endif
@@ -843,10 +707,14 @@ StartUp(Bool defaultScreenOnly)
sig_action.sa_flags = SA_RESTART;
sigaction(SIGQUIT, &sig_action, NULL);
/* instead of catching these, we let the default handler abort the
* program. The new monitor process will take appropriate action
* when it detects the crash.
sigaction(SIGSEGV, &sig_action, NULL);
sigaction(SIGBUS, &sig_action, NULL);
sigaction(SIGFPE, &sig_action, NULL);
sigaction(SIGABRT, &sig_action, NULL);
*/
sig_action.sa_handler = handleExitSig;
@@ -971,12 +839,9 @@ StartUp(Bool defaultScreenOnly)
/* initialize/restore state for the screens */
for (j = 0; j < wScreenCount; j++) {
int crashed;
int lastDesktop;
/* restore workspace state */
if (!getWorkspaceState(wScreen[j]->root_win, &ws_state)) {
ws_state = NULL;
}
lastDesktop= wNETWMGetCurrentDesktopFromHint(wScreen[j]);
wScreenRestoreState(wScreen[j]);
@@ -984,18 +849,13 @@ StartUp(Bool defaultScreenOnly)
if (!wPreferences.flags.nodock && wScreen[j]->dock)
wScreen[j]->last_dock = wScreen[j]->dock;
if (ws_state && (ws_state->flags & WFLAGS_CRASHED)!=0)
crashed = 1;
else
crashed = 0;
manageAllWindows(wScreen[j], crashed);
manageAllWindows(wScreen[j], wPreferences.flags.restarting==2);
/* restore saved menus */
wMenuRestoreState(wScreen[j]);
/* If we're not restarting restore session */
if (ws_state == NULL && !wPreferences.flags.norestore)
/* If we're not restarting, restore session */
if (wPreferences.flags.restarting==0 && !wPreferences.flags.norestore)
wSessionRestoreState(wScreen[j]);
if (!wPreferences.flags.noautolaunch) {
@@ -1017,9 +877,8 @@ StartUp(Bool defaultScreenOnly)
}
/* go to workspace where we were before restart */
if (ws_state) {
wWorkspaceForceChange(wScreen[j], ws_state->workspace);
wfree(ws_state);
if (lastDesktop >= 0) {
wWorkspaceForceChange(wScreen[j], lastDesktop);
} else {
wSessionRestoreLastWorkspace(wScreen[j]);
}

View File

@@ -62,10 +62,8 @@
/* #define CPP_PATH @CPP_PATH@ */
/*
* support for OffiX DND drag and drop in the Dock
*/
#define OFFIX_DND
#define NETWM_HINTS
/*
* support for XDND drop in the Dock. Experimental

View File

@@ -574,7 +574,7 @@ fixLeaderProperties(WWindow *wwin)
classHint = XAllocClassHint();
clientHints = XGetWMHints(dpy, wwin->client_win);
pid = GetPidForWindow(wwin->client_win);
pid = wNETWMGetPidForWindow(wwin->client_win);
if (pid > 0) {
haveCommand = GetCommandForPid(pid, &argv, &argc);
} else {

View File

@@ -40,6 +40,7 @@
#include "icon.h"
#include "stacking.h"
#include "xinerama.h"
#include "properties.h"
#ifdef DEBUG_WMSPEC
@@ -348,6 +349,24 @@ wNETWMUpdateDesktop(WScreen *scr)
}
int
wNETWMGetCurrentDesktopFromHint(WScreen *scr)
{
int count;
unsigned char *prop;
prop= PropGetCheckProperty(scr->root_win, net_current_desktop, XA_CARDINAL,
0, 1, &count);
if (prop)
{
int desktop= *(CARD32*)prop;
XFree(prop);
return desktop;
}
return -1;
}
static void
updateIconImage(WScreen *scr, WWindow *wwin)
{
@@ -509,7 +528,6 @@ wNETWMInitStuff(WScreen *scr)
updateClientList(scr);
updateClientListStacking(scr, NULL);
updateWorkspaceCount(scr);
updateCurrentWorkspace(scr);
updateWorkspaceNames(scr);
updateShowDesktop(scr, False);

View File

@@ -41,5 +41,5 @@ void wNETWMUpdateActions(WWindow *wwin, Bool del);
void wNETWMUpdateDesktop(WScreen *scr);
void wNETWMPositionSplash(WWindow *wwin, int *x, int *y, int width, int height);
int wNETWMGetPidForWindow(Window window);
int wNETWMGetCurrentDesktopFromHint(WScreen *scr);
#endif