Kaydet (Commit) 86a168fb authored tarafından Nick Treleaven's avatar Nick Treleaven

Change utils_str_remove_chars() to work in place; fix allocating on

the stack (the string length could exhaust the stack size).



git-svn-id: https://geany.svn.sourceforge.net/svnroot/geany/trunk@4012 ea778897-0a13-0410-b9d1-a72fbfd435f5
üst 39a74c5a
2009-07-23 Nick Treleaven <nick(dot)treleaven(at)btinternet(dot)com>
* src/utils.c, src/utils.h, src/toolbar.c, src/plugindata.h,
plugins/splitwindow.c:
Change utils_str_remove_chars() to work in place; fix allocating on
the stack (the string length could exhaust the stack size).
2009-07-21 Enrico Tröger <enrico(dot)troeger(at)uvena(dot)de> 2009-07-21 Enrico Tröger <enrico(dot)troeger(at)uvena(dot)de>
* src/utils.c: * src/utils.c:
......
...@@ -223,8 +223,9 @@ static const gchar *ui_get_stock_label(const gchar *stock_id) ...@@ -223,8 +223,9 @@ static const gchar *ui_get_stock_label(const gchar *stock_id)
} }
/* Create a GtkToolButton with stock icon and tooltip. /* Create a GtkToolButton with stock icon, label and tooltip.
* @param label can be NULL to use stock label text, without underscores. * @param label can be NULL to use stock label text. @a label can contain underscores,
* which will be removed.
* @param tooltip can be NULL to use label text (useful for GTK_TOOLBAR_ICONS). */ * @param tooltip can be NULL to use label text (useful for GTK_TOOLBAR_ICONS). */
static GtkWidget *ui_tool_button_new(const gchar *stock_id, const gchar *label, const gchar *tooltip) static GtkWidget *ui_tool_button_new(const gchar *stock_id, const gchar *label, const gchar *tooltip)
{ {
...@@ -234,9 +235,10 @@ static GtkWidget *ui_tool_button_new(const gchar *stock_id, const gchar *label, ...@@ -234,9 +235,10 @@ static GtkWidget *ui_tool_button_new(const gchar *stock_id, const gchar *label,
if (stock_id && !label) if (stock_id && !label)
{ {
label = ui_get_stock_label(stock_id); label = ui_get_stock_label(stock_id);
dup = utils_str_remove_chars(label, "_");
label = dup;
} }
dup = utils_str_remove_chars(g_strdup(label), "_");
label = dup;
item = gtk_tool_button_new(NULL, label); item = gtk_tool_button_new(NULL, label);
if (stock_id) if (stock_id)
gtk_tool_button_set_stock_id(GTK_TOOL_BUTTON(item), stock_id); gtk_tool_button_set_stock_id(GTK_TOOL_BUTTON(item), stock_id);
...@@ -266,7 +268,6 @@ static GtkWidget *create_toolbar(void) ...@@ -266,7 +268,6 @@ static GtkWidget *create_toolbar(void)
{ {
GtkWidget *toolbar, *item; GtkWidget *toolbar, *item;
GtkToolItem *tool_item; GtkToolItem *tool_item;
gchar *label;
toolbar = gtk_toolbar_new(); toolbar = gtk_toolbar_new();
gtk_toolbar_set_icon_size(GTK_TOOLBAR(toolbar), GTK_ICON_SIZE_MENU); gtk_toolbar_set_icon_size(GTK_TOOLBAR(toolbar), GTK_ICON_SIZE_MENU);
...@@ -286,11 +287,9 @@ static GtkWidget *create_toolbar(void) ...@@ -286,11 +287,9 @@ static GtkWidget *create_toolbar(void)
gtk_container_add(GTK_CONTAINER(tool_item), item); gtk_container_add(GTK_CONTAINER(tool_item), item);
edit_window.name_label = item; edit_window.name_label = item;
label = utils_str_remove_chars(_("_Unsplit"), "_"); item = ui_tool_button_new(GTK_STOCK_CLOSE, _("_Unsplit"), NULL);
item = ui_tool_button_new(GTK_STOCK_CLOSE, label, NULL);
gtk_container_add(GTK_CONTAINER(toolbar), item); gtk_container_add(GTK_CONTAINER(toolbar), item);
g_signal_connect(item, "clicked", G_CALLBACK(on_unsplit), NULL); g_signal_connect(item, "clicked", G_CALLBACK(on_unsplit), NULL);
g_free(label);
return toolbar; return toolbar;
} }
......
...@@ -50,13 +50,13 @@ ...@@ -50,13 +50,13 @@
enum { enum {
/** The Application Programming Interface (API) version, incremented /** The Application Programming Interface (API) version, incremented
* whenever any plugin data types are modified or appended to. */ * whenever any plugin data types are modified or appended to. */
GEANY_API_VERSION = 148, GEANY_API_VERSION = 149,
/** The Application Binary Interface (ABI) version, incremented whenever /** The Application Binary Interface (ABI) version, incremented whenever
* existing fields in the plugin data types have to be changed or reordered. */ * existing fields in the plugin data types have to be changed or reordered. */
/* This should usually stay the same if fields are only appended, assuming only pointers to /* This should usually stay the same if fields are only appended, assuming only pointers to
* structs and not structs themselves are declared by plugins. */ * structs and not structs themselves are declared by plugins. */
GEANY_ABI_VERSION = 62 GEANY_ABI_VERSION = 63
}; };
/** Check the plugin can be loaded by Geany. /** Check the plugin can be loaded by Geany.
...@@ -369,7 +369,7 @@ typedef struct UtilsFuncs ...@@ -369,7 +369,7 @@ typedef struct UtilsFuncs
guint (*string_replace_first) (GString *haystack, const gchar *needle, guint (*string_replace_first) (GString *haystack, const gchar *needle,
const gchar *replace); const gchar *replace);
gchar* (*str_middle_truncate) (const gchar *string, guint truncate_length); gchar* (*str_middle_truncate) (const gchar *string, guint truncate_length);
gchar* (*str_remove_chars) (const gchar *string, const gchar *chars); gchar* (*str_remove_chars) (gchar *string, const gchar *chars);
} }
UtilsFuncs; UtilsFuncs;
......
...@@ -625,7 +625,7 @@ static void tb_editor_set_item_values(const gchar *name, GtkListStore *store, Gt ...@@ -625,7 +625,7 @@ static void tb_editor_set_item_values(const gchar *name, GtkListStore *store, Gt
g_object_get(action, "label", &label, NULL); g_object_get(action, "label", &label, NULL);
if (label != NULL) if (label != NULL)
label_clean = utils_str_remove_chars(label, "_"); label_clean = utils_str_remove_chars(g_strdup(label), "_");
} }
gtk_list_store_set(store, iter, gtk_list_store_set(store, iter,
......
...@@ -1756,49 +1756,37 @@ void utils_tidy_path(gchar *filename) ...@@ -1756,49 +1756,37 @@ void utils_tidy_path(gchar *filename)
} }
/* Like strcpy, but can handle overlapping src and dest. */ /* @warning Doesn't include null terminating character. */
static gchar *utils_str_copy(gchar *dest, const gchar *src) #define foreach_str(char_ptr, string) \
{ for (char_ptr = string; *char_ptr; char_ptr++)
gchar *cpy;
/* strcpy might not handle overlaps, so make a copy */
cpy = utils_strdupa(src);
return strcpy(dest, cpy);
}
/** /**
* Remove characters from a string. * Replace or remove characters from a string in place.
* *
* @param string The original string * @param string String to search.
* @param chars Characters to remove. * @param chars Characters to remove.
* *
* @return A newly-allocated copy of @a str without the characters in @a chars, * @return @a string - return value is only useful when nesting function calls, e.g.:
* should be freed when no longer needed. * @code str = utils_str_remove_chars(g_strdup("f_o_o"), "_"); @endcode
*
* @see @c g_strdelimit.
**/ **/
gchar *utils_str_remove_chars(const gchar *string, const gchar *chars) gchar *utils_str_remove_chars(gchar *string, const gchar *chars)
{ {
gchar *ptr; const gchar *r;
gchar *result; gchar *w = string;
gsize len;
g_return_val_if_fail(string, NULL); g_return_val_if_fail(string, NULL);
if (!NZV(chars))
return string;
result = g_strdup(string); foreach_str(r, string)
len = strlen(result);
ptr = result;
while (ptr < result + len)
{ {
if (strchr(chars, *ptr)) if (!strchr(chars, *r))
{ *w++ = *r;
utils_str_copy(ptr, ptr + 1);
len--;
}
else
ptr++;
} }
return result; *w = 0x0;
return string;
} }
...@@ -198,6 +198,6 @@ gboolean utils_is_remote_path(const gchar *path); ...@@ -198,6 +198,6 @@ gboolean utils_is_remote_path(const gchar *path);
gchar *utils_str_middle_truncate(const gchar *string, guint truncate_length); gchar *utils_str_middle_truncate(const gchar *string, guint truncate_length);
gchar *utils_str_remove_chars(const gchar *string, const gchar *chars); gchar *utils_str_remove_chars(gchar *string, const gchar *chars);
#endif #endif
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment