summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorsabetts <sabetts>2003-02-27 12:33:00 +0000
committersabetts <sabetts>2003-02-27 12:33:00 +0000
commit293fca91a75f15c696c2f1d9dd4227f558cfc26f (patch)
tree9fa4d15ede6975b561b07d4d8004c0885c8124fd
parent6b341ac568efd980ddbbbfbb2c4960204879afdb (diff)
downloadratpoison-293fca91a75f15c696c2f1d9dd4227f558cfc26f.zip
* src/main.c (free_screen): new function
(clean_up): call free_screen on each screen. free the screen array. free defaults.window_fmt. * src/number.h (free_numbers): new prototype * src/number.c (free_numbers): new function * src/manage.c (get_wmname): use XGetWindowProperty to get the window name. (unmanaged_window): free wname after using it. * src/main.c (wm_name): new global (main): internalize WM_NAME atom. (clean_up): free data structures for keybindings, aliases, the bar, window numbers, and input history. * src/input.h (free_history): new prototype * src/input.c (free_history): new function * src/events.c (execute_remote_command): free properties returned by XGetWindowProperty(). * src/data.h (wm_name): new extern * src/communications.c (recieve_command_result): free properties returned by XGetWindowProperty(). * src/bar.h (free_bar): new prototype * src/bar.c (update_window_names): bar_buffer is not static. (update_window_names): free bar_buffer after using it. (marked_message): free the GC after using it. (free_bar): new function. * src/actions.h (free_keybindings): new prototype (free_aliases): likewise * src/actions.c (free_keybindings): new function (free_aliases): likewise (cmd_tmpwm): unmap the key window before calling the new wm, and remap it afterwards.
-rw-r--r--ChangeLog51
-rw-r--r--src/actions.c39
-rw-r--r--src/actions.h2
-rw-r--r--src/bar.c17
-rw-r--r--src/bar.h1
-rw-r--r--src/communications.c55
-rw-r--r--src/data.h1
-rw-r--r--src/events.c41
-rw-r--r--src/input.c9
-rw-r--r--src/input.h1
-rw-r--r--src/list.c2
-rw-r--r--src/main.c44
-rw-r--r--src/manage.c47
-rw-r--r--src/number.c6
-rw-r--r--src/number.h1
15 files changed, 243 insertions, 74 deletions
diff --git a/ChangeLog b/ChangeLog
index d2ef973..8a235e8 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,54 @@
+2003-02-27 Shawn Betts <sabetts@sfu.ca>
+
+ * src/main.c (free_screen): new function
+ (clean_up): call free_screen on each screen. free the screen
+ array. free defaults.window_fmt.
+
+ * src/number.h (free_numbers): new prototype
+
+ * src/number.c (free_numbers): new function
+
+ * src/manage.c (get_wmname): use XGetWindowProperty to get the
+ window name.
+ (unmanaged_window): free wname after using it.
+
+ * src/main.c (wm_name): new global
+ (main): internalize WM_NAME atom.
+ (clean_up): free data structures for keybindings, aliases, the
+ bar, window numbers, and input history.
+
+ * src/input.h (free_history): new prototype
+
+ * src/input.c (free_history): new function
+
+ * src/events.c (execute_remote_command): free properties returned
+ by XGetWindowProperty().
+
+ * src/data.h (wm_name): new extern
+
+ * src/communications.c (recieve_command_result): free properties
+ returned by XGetWindowProperty().
+
+ * src/bar.h (free_bar): new prototype
+
+ * src/bar.c (update_window_names): bar_buffer is not static.
+ (update_window_names): free bar_buffer after using it.
+ (marked_message): free the GC after using it.
+ (free_bar): new function.
+
+ * src/actions.h (free_keybindings): new prototype
+ (free_aliases): likewise
+
+ * src/actions.c (free_keybindings): new function
+ (free_aliases): likewise
+ (cmd_tmpwm): unmap the key window before calling the new wm, and
+ remap it afterwards.
+
+2003-02-24 Shawn Betts <sabetts@sfu.ca>
+
+ * src/actions.c (cmd_tmpwm): unmap the key window before spawning
+ the wm and map it afterwards.
+
2003-02-23 Shawn Betts <sabetts@sfu.ca>
* src/split.c (remove_all_splits): fix bug hiding windows not in
diff --git a/src/actions.c b/src/actions.c
index a6e89e4..28a583e 100644
--- a/src/actions.c
+++ b/src/actions.c
@@ -344,6 +344,37 @@ initialize_default_keybindings (void)
add_keybinding (XK_question, 0, "help");
}
+void
+free_keybindings ()
+{
+ int i;
+
+ /* Free the data in the actions. */
+ for (i=0; i<key_actions_last; i++)
+ {
+ free (key_actions[i].data);
+ }
+
+ /* Free the actions list. */
+ free (key_actions);
+}
+
+void
+free_aliases ()
+{
+ int i;
+
+ /* Free the alias data. */
+ for (i=0; i<alias_list_last; i++)
+ {
+ free (alias_list[i].name);
+ free (alias_list[i].alias);
+ }
+
+ /* Free the alias list. */
+ free (alias_list);
+}
+
/* return a KeySym from a string that contains either a hex value or
an X keysym description */
static int string_to_keysym (char *str)
@@ -2732,7 +2763,11 @@ cmd_tmpwm (int interactive, void *data)
/* Release event selection on the root windows, so the new WM can
have it. */
for (i=0; i<num_screens; i++)
- XSelectInput(dpy, RootWindow (dpy, i), 0);
+ {
+ XSelectInput(dpy, RootWindow (dpy, i), 0);
+ /* Unmap its key window */
+ XUnmapWindow (dpy, screens[i].key_window);
+ }
/* Don't listen for any events from any window. */
list_for_each_safe_entry (win, iter, tmp, &rp_mapped_window, node)
@@ -2773,6 +2808,8 @@ cmd_tmpwm (int interactive, void *data)
XSelectInput(dpy, RootWindow (dpy, i),
PropertyChangeMask | ColormapChangeMask
| SubstructureRedirectMask | SubstructureNotifyMask);
+ /* Map its key window */
+ XMapWindow (dpy, screens[i].key_window);
}
XSync (dpy, False);
diff --git a/src/actions.h b/src/actions.h
index e383f74..643bec5 100644
--- a/src/actions.h
+++ b/src/actions.h
@@ -118,6 +118,8 @@ char *cmd_warp(int interactive, void *data);
char *cmd_tmpwm (int interactive, void *data);
void initialize_default_keybindings (void);
+void free_keybindings ();
+void free_aliases ();
rp_action* find_keybinding (KeySym keysym, int state);
rp_action* find_keybinding_by_action (char *action);
diff --git a/src/bar.c b/src/bar.c
index 547e4e2..d363305 100644
--- a/src/bar.c
+++ b/src/bar.c
@@ -138,19 +138,18 @@ bar_y (screen_info *s)
void
update_window_names (screen_info *s)
{
- static struct sbuf *bar_buffer = NULL;
-
+ struct sbuf *bar_buffer;
int mark_start = 0;
int mark_end = 0;
if (s->bar_is_raised != BAR_IS_WINDOW_LIST) return;
- if (bar_buffer == NULL)
- bar_buffer = sbuf_new (0);
+ bar_buffer = sbuf_new (0);
get_window_list (defaults.window_fmt, NULL, bar_buffer, &mark_start, &mark_end);
marked_message (sbuf_get (bar_buffer), mark_start, mark_end);
+ sbuf_free (bar_buffer);
}
void
@@ -253,11 +252,13 @@ marked_message (char *msg, int mark_start, int mark_end)
lgc = XCreateGC(dpy, s->root, mask, &lgv);
XFillRectangle (dpy, s->bar_window, lgc, start, 0, width, height);
+ XFreeGC (dpy, lgc);
lgv.foreground = s->bg_color;
lgc = XCreateGC(dpy, s->root, mask, &lgv);
XFillRectangle (dpy, s->bar_window, lgc, start, 0, width, height);
+ XFreeGC (dpy, lgc);
}
/* Keep a record of the message. */
@@ -283,3 +284,11 @@ show_last_message ()
marked_message (msg, last_mark_start, last_mark_end);
free (msg);
}
+
+/* Free any memory associated with the bar. */
+void
+free_bar ()
+{
+ if (last_msg)
+ free (last_msg);
+}
diff --git a/src/bar.h b/src/bar.h
index d2b7dc6..5ec1262 100644
--- a/src/bar.h
+++ b/src/bar.h
@@ -32,5 +32,6 @@ int bar_x (screen_info *s, int width);
void marked_message (char *msg, int hl_start, int hl_end);
void marked_message_printf (int mark_start, int mark_end, char *fmt, ...);
void show_last_message ();
+void free_bar ();
#endif /* ! _RATPOISON_BAR_H */
diff --git a/src/communications.c b/src/communications.c
index 9818ae6..7705c85 100644
--- a/src/communications.c
+++ b/src/communications.c
@@ -34,29 +34,50 @@
static void
recieve_command_result (Window w)
{
+ int status;
Atom type_ret;
int format_ret;
unsigned long nitems;
unsigned long bytes_after;
- unsigned char *result;
-
-
- if (XGetWindowProperty (dpy, w, rp_command_result,
- 0, 0, False, XA_STRING,
- &type_ret, &format_ret, &nitems, &bytes_after,
- &result) == Success
- &&
- XGetWindowProperty (dpy, w, rp_command_result,
- 0, (bytes_after / 4) + (bytes_after % 4 ? 1 : 0),
- True, XA_STRING, &type_ret, &format_ret, &nitems,
- &bytes_after, &result) == Success)
+ unsigned char *result = NULL;
+
+ /* First, find out how big the property is. */
+ status = XGetWindowProperty (dpy, w, rp_command_result,
+ 0, 0, False, XA_STRING,
+ &type_ret, &format_ret, &nitems, &bytes_after,
+ &result);
+
+ /* Failed to retrieve property. */
+ if (status != Success || result == NULL)
{
- if (result && strlen (result))
- {
- printf ("%s\n", result);
- }
- XFree (result);
+ PRINT_DEBUG (("failed to get command result length\n"));
+ return;
}
+
+ /* XGetWindowProperty always allocates one extra byte even if
+ the property is zero length. */
+ XFree (result);
+
+ /* Now that we have the length of the message, we can get the
+ whole message. */
+ status = XGetWindowProperty (dpy, w, rp_command_result,
+ 0, (bytes_after / 4) + (bytes_after % 4 ? 1 : 0),
+ True, XA_STRING, &type_ret, &format_ret, &nitems,
+ &bytes_after, &result);
+
+ /* Failed to retrieve property. */
+ if (status != Success || result == NULL)
+ {
+ PRINT_DEBUG (("failed to get command result\n"));
+ return;
+ }
+
+ /* If result is not the empty string, print it. */
+ if (strlen (result))
+ printf ("%s\n", result);
+
+ /* Free the result. */
+ XFree (result);
}
int
diff --git a/src/data.h b/src/data.h
index d3b2e9e..235517b 100644
--- a/src/data.h
+++ b/src/data.h
@@ -213,6 +213,7 @@ extern Atom rp_command;
extern Atom rp_command_request;
extern Atom rp_command_result;
+extern Atom wm_name;
extern Atom wm_state;
extern Atom wm_change_state;
extern Atom wm_protocols;
diff --git a/src/events.c b/src/events.c
index c66c938..dd998b5 100644
--- a/src/events.c
+++ b/src/events.c
@@ -441,6 +441,7 @@ key_press (XEvent *ev)
static char *
execute_remote_command (Window w)
{
+ int status;
char *result = NULL;
Atom type_ret;
int format_ret;
@@ -448,28 +449,36 @@ execute_remote_command (Window w)
unsigned long bytes_after;
unsigned char *req;
- if (XGetWindowProperty (dpy, w, rp_command,
- 0, 0, False, XA_STRING,
- &type_ret, &format_ret, &nitems, &bytes_after,
- &req) == Success
- &&
- XGetWindowProperty (dpy, w, rp_command,
- 0, (bytes_after / 4) + (bytes_after % 4 ? 1 : 0),
- True, XA_STRING, &type_ret, &format_ret, &nitems,
- &bytes_after, &req) == Success)
+ status = XGetWindowProperty (dpy, w, rp_command,
+ 0, 0, False, XA_STRING,
+ &type_ret, &format_ret, &nitems, &bytes_after,
+ &req);
+
+ if (status != Success || req == NULL)
{
- if (req)
- {
- PRINT_DEBUG (("command: %s\n", req));
- result = command (0, req);
- }
- XFree (req);
+ PRINT_DEBUG (("Couldn't get RP_COMMAND Property\n"));
+ return NULL;
}
- else
+
+ /* XGetWindowProperty always allocates one extra byte even if
+ the property is zero length. */
+ XFree (req);
+
+ status = XGetWindowProperty (dpy, w, rp_command,
+ 0, (bytes_after / 4) + (bytes_after % 4 ? 1 : 0),
+ True, XA_STRING, &type_ret, &format_ret, &nitems,
+ &bytes_after, &req);
+
+ if (status != Success || req == NULL)
{
PRINT_DEBUG (("Couldn't get RP_COMMAND Property\n"));
+ return NULL;
}
+ PRINT_DEBUG (("command: %s\n", req));
+ result = command (0, req);
+ XFree (req);
+
return result;
}
diff --git a/src/input.c b/src/input.c
index 1f46508..6064d93 100644
--- a/src/input.c
+++ b/src/input.c
@@ -455,3 +455,12 @@ get_more_input (char *prompt, char *preinput)
XUnmapWindow (dpy, s->input_window);
return str;
}
+
+void
+free_history ()
+{
+ int i;
+
+ for (i=0; i<input_num_history_entries; i++)
+ free (input_history[i]);
+}
diff --git a/src/input.h b/src/input.h
index 65e4607..0544f37 100644
--- a/src/input.h
+++ b/src/input.h
@@ -31,5 +31,6 @@ unsigned int x11_mask_to_rp_mask (unsigned int mask);
unsigned int rp_mask_to_x11_mask (unsigned int mask);
void update_modifier_map ();
void grab_key (int keycode, unsigned int modifiers, Window grab_window);
+void free_history ();
#endif /* ! _RATPOISON_INPUT_H */
diff --git a/src/list.c b/src/list.c
index fa66e36..12d51c8 100644
--- a/src/list.c
+++ b/src/list.c
@@ -51,7 +51,7 @@ free_window (rp_window *w)
free (w->wm_name);
XFree (w->hints);
-
+
free (w);
}
diff --git a/src/main.c b/src/main.c
index 29ce345..4c31511 100644
--- a/src/main.c
+++ b/src/main.c
@@ -47,6 +47,7 @@ int rat_x;
int rat_y;
int rat_visible = 1; /* rat is visible by default */
+Atom wm_name;
Atom wm_state;
Atom wm_change_state;
Atom wm_protocols;
@@ -555,6 +556,7 @@ main (int argc, char *argv[])
}
/* Set our Atoms */
+ wm_name = XInternAtom(dpy, "WM_NAME", False);
wm_state = XInternAtom(dpy, "WM_STATE", False);
wm_change_state = XInternAtom(dpy, "WM_CHANGE_STATE", False);
wm_protocols = XInternAtom(dpy, "WM_PROTOCOLS", False);
@@ -696,25 +698,49 @@ init_screen (screen_info *s, int screen_num)
XSync (dpy, 0);
}
+static void
+free_screen (screen_info *s)
+{
+ rp_window_frame *frame;
+ struct list_head *iter, *tmp;
+
+ list_for_each_safe_entry (frame, iter, tmp, &s->rp_window_frames, node)
+ {
+ free (frame);
+ }
+
+ XDestroyWindow (dpy, s->bar_window);
+ XDestroyWindow (dpy, s->key_window);
+ XDestroyWindow (dpy, s->input_window);
+ XDestroyWindow (dpy, s->frame_window);
+ XDestroyWindow (dpy, s->help_window);
+
+ XFreeCursor (dpy, s->rat);
+ XFreeColormap (dpy, s->def_cmap);
+ XFreeGC (dpy, s->normal_gc);
+
+ free (s->display_string);
+}
+
void
clean_up ()
{
int i;
+ free_keybindings ();
+ free_aliases ();
+ free_bar ();
+ free_numbers ();
+ free_history ();
+
for (i=0; i<num_screens; i++)
{
- XDestroyWindow (dpy, screens[i].bar_window);
- XDestroyWindow (dpy, screens[i].key_window);
- XDestroyWindow (dpy, screens[i].input_window);
- XDestroyWindow (dpy, screens[i].frame_window);
- XDestroyWindow (dpy, screens[i].help_window);
-
- XFreeCursor (dpy, screens[i].rat);
- XFreeColormap (dpy, screens[i].def_cmap);
- XFreeGC (dpy, screens[i].normal_gc);
+ free_screen (&screens[i]);
}
+ free (screens);
XFreeFont (dpy, defaults.font);
+ free (defaults.window_fmt);
XSetInputFocus (dpy, PointerRoot, RevertToPointerRoot, CurrentTime);
XCloseDisplay (dpy);
diff --git a/src/manage.c b/src/manage.c
index 451c809..1cdb66a 100644
--- a/src/manage.c
+++ b/src/manage.c
@@ -92,37 +92,30 @@ update_normal_hints (rp_window *win)
static char *
get_wmname (Window w)
{
- char *name;
- XTextProperty text;
- char **name_list;
- int list_len;
-
- if (!XGetWMName (dpy, w, &text))
+ Atom actual_type;
+ int actual_format;
+ int status;
+ unsigned long n;
+ unsigned long bytes_after;
+ unsigned char *name = NULL;
+ char *ret;
+
+ status = XGetWindowProperty (dpy, w, wm_name, 0L, 100L, False,
+ XA_STRING, &actual_type, &actual_format,
+ &n, &bytes_after, &name);
+
+ if (status != Success || name == NULL)
{
PRINT_DEBUG (("I can't get the WMName.\n"));
return NULL;
}
- if (!XTextPropertyToStringList (&text, &name_list, &list_len))
- {
- PRINT_DEBUG (("Error retrieving TextList.\n"));
- return NULL;
- }
+ /* duplicate the string into out own buffer, and free the one given
+ to us by X. */
+ ret = xstrdup (name);
+ XFree (name);
- if (list_len > 0)
- {
- name = xmalloc (strlen (name_list[0]) + 1);
- strcpy (name, name_list[0]);
- }
- else
- {
- name = NULL;
- }
-
- /* Its our responsibility to free this. */
- XFreeStringList (name_list);
-
- return name;
+ return ret;
}
static XClassHint *
@@ -276,7 +269,7 @@ unmanage (rp_window *w)
{
return_window_number (w->number);
list_del (&w->node);
- free_window (w);
+ free_window (w);
#ifdef AUTO_CLOSE
if (rp_mapped_window_sentinel->next == rp_mapped_window_sentinel
@@ -353,6 +346,8 @@ unmanaged_window (Window w)
free (wname);
return 1;
}
+
+ free (wname);
}
return 0;
diff --git a/src/number.c b/src/number.c
index 8676d9d..0dfd2cf 100644
--- a/src/number.c
+++ b/src/number.c
@@ -119,3 +119,9 @@ init_numbers ()
numbers_taken = xmalloc (max_taken * sizeof (int));
}
+
+void
+free_numbers ()
+{
+ free (numbers_taken);
+}
diff --git a/src/number.h b/src/number.h
index aea0945..caecff5 100644
--- a/src/number.h
+++ b/src/number.h
@@ -26,5 +26,6 @@ int get_unique_window_number ();
void return_window_number (int n);
int add_window_number (int n);
void init_numbers ();
+void free_numbers ();
#endif /* ! _RATPOISON_NUMBER_H */